summaryrefslogtreecommitdiffstats
path: root/tools
diff options
context:
space:
mode:
authorTim Jenssen <tim.jenssen@nokia.com>2011-03-08 20:46:27 +0100
committerTim Jenssen <tim.jenssen@nokia.com>2011-03-09 11:05:24 +0100
commit64391c88c7e1421dd146b528c4395c68049c4adb (patch)
treea9aca3608c546b134ad6d7d2ea8d164d0b008af0 /tools
parent76122d63eced0b083e3c2e701c069aa2a8db360f (diff)
moved some directories and adjusted the README
- also removed some unused projects under examples(updater, updaterplugin) - adjusted pro files to the new structure
Diffstat (limited to 'tools')
-rw-r--r--tools/maddehelper/maddehelper.pro12
-rw-r--r--tools/maddehelper/main.cpp306
-rw-r--r--tools/operationrunner/operationrunner.cpp92
-rw-r--r--tools/operationrunner/operationrunner.pro18
-rw-r--r--tools/repogenfromonlinerepo/downloadmanager.cpp172
-rw-r--r--tools/repogenfromonlinerepo/downloadmanager.h84
-rw-r--r--tools/repogenfromonlinerepo/main.cpp306
-rw-r--r--tools/repogenfromonlinerepo/repogenfromonlinerepo.pro16
-rw-r--r--tools/repogenfromonlinerepo/textprogressbar.cpp98
-rw-r--r--tools/repogenfromonlinerepo/textprogressbar.h63
10 files changed, 1167 insertions, 0 deletions
diff --git a/tools/maddehelper/maddehelper.pro b/tools/maddehelper/maddehelper.pro
new file mode 100644
index 000000000..df9954eba
--- /dev/null
+++ b/tools/maddehelper/maddehelper.pro
@@ -0,0 +1,12 @@
+QT += core
+
+QT -= gui
+
+TARGET = maddehelper
+CONFIG += console
+CONFIG -= app_bundle
+
+TEMPLATE = app
+
+
+SOURCES += main.cpp
diff --git a/tools/maddehelper/main.cpp b/tools/maddehelper/main.cpp
new file mode 100644
index 000000000..1f4ed555b
--- /dev/null
+++ b/tools/maddehelper/main.cpp
@@ -0,0 +1,306 @@
+#include <QCoreApplication>
+#include <QProcess>
+#include <QDebug>
+#include <QDirIterator>
+#include <QDateTime>
+#include <iostream>
+
+//rebase to adress 0x20000000 results in crashing tools like perl on win7/64bit
+//which I used for testing
+bool rebaseDlls(const QString &maddeBinLocation,
+ const QString &rebaseBinaryLocation,
+ const QString &adressValue = "0x50000000",
+ const QString &dllFilter = "msys*.dll")
+{
+ QStringList dllStringList = QDir(maddeBinLocation).entryList(QStringList(dllFilter), QDir::Files, QDir::Size | QDir::Reversed);
+ QString dlls;
+ QString dllsEnd; //of an unknown issue msys-1.0.dll should be the last on my system
+ foreach (QString dll, dllStringList) {
+ dll.prepend(maddeBinLocation + "/");
+ if (dll.contains("msys-1")) {
+ dllsEnd.append(dll + " ");
+ } else {
+ dlls.append(dll + " ");
+ }
+ }
+ dlls = dlls.append(dllsEnd);
+
+ QProcess process;
+ process.setEnvironment(QStringList("EMPTY_ENVIRONMENT=true"));
+ QProcess::ProcessError initError(process.error());
+ process.setProcessChannelMode(QProcess::MergedChannels);
+ process.setNativeArguments(QString("-b %1 -o 0x10000 -v %2").arg(adressValue, dlls));
+ process.start(rebaseBinaryLocation);
+ process.waitForFinished();
+ if (process.exitCode() != 0 ||
+ initError != process.error() ||
+ process.exitStatus() == QProcess::CrashExit)
+ {
+ qWarning() << rebaseBinaryLocation + " " + process.nativeArguments();
+ qWarning() << QString("\t Adress rebasing failed! Maybe a process(bash.exe, ssh, ...) is using some of the dlls(%1).").arg(dllStringList.join(", "));
+ qWarning() << "\t Output: \n" << process.readAll();
+ if (initError != process.error()) {
+ qDebug() << QString("\tError(%1): ").arg(process.error()) << process.errorString();
+ }
+
+ if (process.exitStatus() == QProcess::CrashExit) {
+ qDebug() << "\tcrashed!!!";
+ }
+ return false;
+ }
+ qWarning() << rebaseBinaryLocation + " " + process.nativeArguments();
+ //qWarning() << "\t Output: \n" << process.readAll();
+ return true;
+}
+
+bool checkTools(const QString &maddeBinLocation, const QStringList &binaryCheckList)
+{
+ QDirIterator it( maddeBinLocation, binaryCheckList, QDir::Files );
+ while (it.hasNext()) {
+ QString processPath(it.next());
+ if (!QFileInfo(processPath).exists()) {
+ qDebug() << processPath << " is missing - so we don't need to check it";
+ continue;
+ }
+ bool testedToolState = true;
+ QProcess process;
+ process.setEnvironment(QStringList("EMPTY_ENVIRONMENT=true"));
+ QProcess::ProcessError initError(process.error());
+ process.setProcessChannelMode(QProcess::MergedChannels);
+ process.start(processPath, QStringList("--version"));
+ process.waitForFinished(1000);
+ QString processOutput = process.readAll();
+
+ //check for the unpossible load dll error
+ if (processOutput.contains("VirtualAlloc pointer is null") ||
+ processOutput.contains("Couldn't reserve space for") ||
+ process.exitStatus() == QProcess::CrashExit)
+ {
+ qWarning() << QString("found dll loading problem with(ExitCode: %1): ").arg(QString::number(process.exitCode())) << processPath;
+ qWarning() << processOutput;
+ testedToolState = false;
+ if (initError != process.error()) {
+ qWarning() << QString("\tError(%1): ").arg(process.error()) << process.errorString();
+ }
+
+ if (process.exitStatus() == QProcess::CrashExit) {
+ qWarning() << "\tcrashed!!!";
+ }
+ }
+ if ( process.state() == QProcess::Running )
+ process.terminate();
+ //again wait some time
+ if ( !process.waitForFinished( 1000 ) ) {
+ process.kill();
+ process.waitForFinished( 1000 ); //some more waittime
+ }
+ if (testedToolState == false) {
+ return false;
+ }
+ }
+ return true;
+}
+
+bool removeDirectory( const QString& path )
+{
+ if ( !QFileInfo(path).exists() )
+ return true;
+ if ( path.isEmpty() ) // QDir( "" ) points to the working directory! We never want to remove that one.
+ return true;
+
+ QDirIterator it(path, QDir::NoDotAndDotDot | QDir::AllEntries | QDir::Hidden | QDir::System);
+ while ( it.hasNext() )
+ {
+ it.next();
+ const QFileInfo currentFileInfo = it.fileInfo();
+
+ if ( currentFileInfo.isDir() && !currentFileInfo.isSymLink() )
+ {
+ removeDirectory( currentFileInfo.filePath() );
+ }
+ else
+ {
+ QFile f( currentFileInfo.filePath() );
+ if( !f.remove() )
+ qWarning() << "Can't remove: " << currentFileInfo.absoluteFilePath();
+ }
+ }
+
+ if ( !QDir().rmdir(path))
+ return QDir().rename(path, path + "_" + QDateTime::currentDateTime().toString());
+ return true;
+}
+
+bool cleanUpSubDirectories(const QString &maddeLocation, const QStringList &subDirectoryList, const QStringList &extraFiles)
+{
+ if (maddeLocation.isEmpty()) {
+ qWarning() << "Remove nothing could be result in a broken system ;)";
+ return false;
+ }
+ if (!QFileInfo(maddeLocation).exists()) {
+ qWarning() << QString("Ups, location '%1' is not existing.").arg(maddeLocation);
+ return false;
+ }
+
+ foreach (const QString &subDirectory, subDirectoryList) {
+ bool removed = removeDirectory(maddeLocation + "/" + subDirectory);
+ if (!removed) {
+ qWarning() << "Can't remove " << subDirectory <<" for a clean up step";
+ return false;
+ }
+ }
+ foreach (const QString &fileName, extraFiles) {
+ QFile file(fileName);
+ if (file.exists()) {
+ bool removed = QFile(fileName).remove();
+ if (!removed) {
+ qWarning() << "Can't remove " << extraFiles <<" for a clean up step";
+ }
+ }
+ }
+
+ return true;
+}
+
+bool runInstall(const QString &postinstallCommand, const QString &checkFileForAnOkInstallation)
+{
+ QProcess process;
+ process.setEnvironment(QStringList("EMPTY_ENVIRONMENT=true"));
+ QProcess::ProcessError initError(process.error());
+ process.setProcessChannelMode(QProcess::ForwardedChannels);
+ process.setNativeArguments(postinstallCommand);
+ process.start(QString(), QStringList());
+
+ process.waitForFinished(-1);
+ if (process.exitCode() != 0 ||
+ initError != process.error() ||
+ process.exitStatus() == QProcess::CrashExit)
+ {
+ qWarning() << QString("runInstall(ExitCode: %1) went wrong \n'%2'").arg(QString::number(process.exitCode()), postinstallCommand);
+ if (initError != process.error()) {
+ qDebug() << QString("\tError(%1): ").arg(process.error()) << process.errorString();
+ }
+
+ if (process.exitStatus() == QProcess::CrashExit) {
+ qDebug() << "\tcrashed!!!";
+ }
+ }
+ if ( process.state() == QProcess::Running )
+ process.terminate();
+ //again wait some time
+ if ( !process.waitForFinished( 1000 ) )
+ process.kill();
+
+ return QFileInfo(checkFileForAnOkInstallation).exists();
+}
+
+
+static void printUsage()
+{
+ const QString appName = QFileInfo( QCoreApplication::applicationFilePath() ).fileName();
+ std::cout << "Usage: " << qPrintable(appName) << " -r <rebase_binary> -m <MADDE_directory>" << std::endl;
+ std::cout << "Example:" << std::endl;
+ std::cout << " " << qPrintable(appName) << " -r D:/msysgit_rebase.exe -m D:/Maemo/4.6.2" << std::endl;
+}
+
+
+int main(int argc, char *argv[])
+{
+ QCoreApplication app(argc, argv);
+
+ if ( app.arguments().count() != 5 ) //5. is app name
+ {
+ printUsage();
+ return 6;
+ }
+
+ QString rebaseBinaryLocation;
+ QString maddeLocation;
+ for ( int i = 1; i < app.arguments().size(); ++i ) {
+ if ( app.arguments().at( i ) == QLatin1String( "" ) )
+ continue;
+ if (app.arguments().at(i) == "-r") {
+ i++;
+ rebaseBinaryLocation = app.arguments().at(i);
+ }
+ if (app.arguments().at(i) == "-m") {
+ i++;
+ maddeLocation = app.arguments().at(i);
+ }
+ }
+ if (!QFileInfo(maddeLocation).isDir()) {
+ qDebug() << "MADDE location is not existing.";
+ return 4;
+ }
+ if (!QFileInfo(maddeLocation + "/bin").isDir()) {
+ qDebug() << "It seems that the madde location don't have a 'bin'' directory.";
+ return 5;
+ }
+ QString maddeBinLocation = maddeLocation + "/bin";
+
+ //from qs
+// var envExecutable = installer.value("TargetDir") + "/" + winMaddeSubPath + "/bin/env.exe";
+// var postShell = installer.value("TargetDir") + "/" + winMaddeSubPath + "/postinstall/postinstall.sh";
+// component.addOperation("Execute", "{0,1}", envExecutable, "-i" , "/bin/sh", "--login", postShell, "--nosleepontrap", "showStandardError");
+
+ QString postinstallShell = maddeLocation + "/postinstall/postinstall.sh";
+ //"--nosleepontrap" is not used in our Madde, but later maybe it is there again
+ QString postinstallCommand = maddeBinLocation + QString("/env.exe -i /bin/sh --login %1").arg(postinstallShell + " --nosleepontrap");
+ QString successFileCheck = maddeLocation + "/madbin/mad.cmd";
+ QString directoriesForCleanUpArgument = "sysroots, toolchains, targets, runtimes, wbin";
+ directoriesForCleanUpArgument.remove(" ");
+ QStringList directoriesForCleanUp(directoriesForCleanUpArgument.split(","));
+
+ //this was used for testings
+ //cleanUpSubDirectories(maddeLocation, directoriesForCleanUp, QStringList(successFileCheck));
+
+ bool installationWentFine = runInstall(postinstallCommand, successFileCheck);
+
+ if (installationWentFine)
+ return 0;
+
+
+ QString binaryCheckArgument = ("a2p.exe, basename.exe, bash.exe, bzip2.exe, cat.exe, chmod.exe, cmp.exe, comm.exe, cp.exe, cut.exe, " \
+ "date.exe, diff.exe, diff3.exe, dirname.exe, du.exe, env.exe, expr.exe, find.exe, fold.exe, gawk.exe, " \
+ "grep.exe, gzip.exe, head.exe, id.exe, install.exe, join.exe, less.exe, ln.exe, ls.exe, lzma.exe, m4.exe, " \
+ "make.exe, md5sum.exe, mkdir.exe, mv.exe, od.exe, paste.exe, patch.exe, perl.exe, perl5.6.1.exe, ps.exe, " \
+ "rm.exe, rmdir.exe, sed.exe, sh.exe, sleep.exe, sort.exe, split.exe, ssh-agent.exe, ssh-keygen.exe, " \
+ "stty.exe, tail.exe, tar.exe, tee.exe, touch.exe, tr.exe, true.exe, uname.exe, uniq.exe, vim.exe, wc.exe, xargs.exe");
+ binaryCheckArgument.remove(" ");
+ QStringList binaryCheckList(binaryCheckArgument.split(","));
+
+ QStringList possibleRebaseAdresses;
+ possibleRebaseAdresses << "0x5200000"; //this uses perl
+ possibleRebaseAdresses << "0x30000000";
+ possibleRebaseAdresses << "0x35000000";
+ possibleRebaseAdresses << "0x40000000";
+ possibleRebaseAdresses << "0x60000000";
+ possibleRebaseAdresses << "0x60800000";
+ possibleRebaseAdresses << "0x68000000"; //this uses git
+
+ foreach (const QString &newAdress, possibleRebaseAdresses) {
+ bool rebased = rebaseDlls(maddeBinLocation, rebaseBinaryLocation, newAdress);
+ if (!rebased) {
+ //rebasing is not working
+ return 2;
+ }
+ bool reseted = cleanUpSubDirectories(maddeLocation, directoriesForCleanUp, QStringList(successFileCheck));
+ if (!reseted) {
+ //Madde couldn't reseted to the starting position
+ return 3;
+ }
+ if (!checkTools(maddeBinLocation, binaryCheckList)) {
+ //we need another adress
+ continue;
+ }
+ bool installationWentFine = runInstall(postinstallCommand, successFileCheck);
+
+ if (installationWentFine) {
+ qDebug() << "Rebasing dlls to " << newAdress <<" helped to install MADDE";
+ return 0;
+ }
+ }
+
+ //means rebasing was not helping
+ return 1;
+}
diff --git a/tools/operationrunner/operationrunner.cpp b/tools/operationrunner/operationrunner.cpp
new file mode 100644
index 000000000..242aa9866
--- /dev/null
+++ b/tools/operationrunner/operationrunner.cpp
@@ -0,0 +1,92 @@
+/**************************************************************************
+**
+** This file is part of Qt SDK**
+**
+** Copyright (c) 2011 Nokia Corporation and/or its subsidiary(-ies).*
+**
+** Contact: Nokia Corporation qt-info@nokia.com**
+**
+** No Commercial Usage
+**
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+**
+** This file may be used under the terms of the GNU Lesser General Public
+** License version 2.1 as published by the Free Software Foundation and
+** appearing in the file LICENSE.LGPL included in the packaging of this file.
+** Please review the following information to ensure the GNU Lesser General
+** Public License version 2.1 requirements will be met:
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception version
+** 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you are unsure which license is appropriate for your use, please contact
+** (qt-info@nokia.com).
+**
+**************************************************************************/
+#include <common/errors.h>
+#include <common/utils.h>
+#include <common/repositorygen.h>
+#include <common/installersettings.h>
+
+#include <init.h>
+#include <KDUpdater/UpdateOperation>
+#include <KDUpdater/UpdateOperationFactory>
+
+#include <QCoreApplication>
+#include <QFileInfo>
+#include <QString>
+#include <QStringList>
+
+#include <iostream>
+
+static void printUsage()
+{
+ std::cout << "Usage: " << std::endl;
+ std::cout << std::endl;
+ std::cout << "operationrunner \"Execute\" \"{0,1}\" \"C:\\Windows\\System32\\cmd.exe\" \"/A\" \"/Q\" \"/C\" \"magicmaemoscript.bat\" \"showStandardError\"" << std::endl;
+}
+
+int main(int argc, char **argv)
+{
+ try {
+ QCoreApplication app(argc, argv);
+
+ QStringList argumentList = app.arguments();
+
+ if( argumentList.count() < 2 || argumentList.contains("--help") )
+ {
+ printUsage();
+ return 1;
+ }
+ argumentList.removeFirst(); // we don't need the application name
+
+ QInstaller::init();
+
+ QInstaller::setVerbose( true );
+
+ QString operationName = argumentList.takeFirst();
+ KDUpdater::UpdateOperation* const operation = KDUpdater::UpdateOperationFactory::instance().create( operationName );
+ if (!operation) {
+ std::cerr << "Can not find the operation: " << qPrintable(operationName) << std::endl;
+ return 1;
+ }
+ operation->setArguments(argumentList);
+ bool readyPerformed = operation->performOperation();
+ if (readyPerformed) {
+ std::cout << "Operation was succesfully performed." << std::endl;
+ } else {
+ std::cerr << "There was a problem while performing the operation: " << qPrintable(operation->errorString()) << std::endl;
+ }
+ return 0;
+ } catch ( const QInstaller::Error& e ) {
+ std::cerr << qPrintable(e.message()) << std::endl;
+ }
+ return 1;
+}
diff --git a/tools/operationrunner/operationrunner.pro b/tools/operationrunner/operationrunner.pro
new file mode 100644
index 000000000..d2f1b05cc
--- /dev/null
+++ b/tools/operationrunner/operationrunner.pro
@@ -0,0 +1,18 @@
+TEMPLATE = app
+TARGET = operationrunner
+DEPENDPATH += . .. ../../installerbuilder/common
+INCLUDEPATH += . ..
+
+DESTDIR = ../../installerbuilder/bin
+
+CONFIG += console
+CONFIG -= app_bundle
+
+QT += xml
+
+include(../../installerbuilder/libinstaller/libinstaller.pri)
+
+# Input
+SOURCES += operationrunner.cpp
+
+LIBS = -L../../installerbuilder/lib -linstaller $$LIBS
diff --git a/tools/repogenfromonlinerepo/downloadmanager.cpp b/tools/repogenfromonlinerepo/downloadmanager.cpp
new file mode 100644
index 000000000..61bf7ea88
--- /dev/null
+++ b/tools/repogenfromonlinerepo/downloadmanager.cpp
@@ -0,0 +1,172 @@
+/****************************************************************************
+**
+** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the examples of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** You may use this file under the terms of the BSD license as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor
+** the names of its contributors may be used to endorse or promote
+** products derived from this software without specific prior written
+** permission.
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "downloadmanager.h"
+
+#include <QFileInfo>
+#include <QNetworkRequest>
+#include <QNetworkReply>
+#include <QString>
+#include <QStringList>
+#include <QTimer>
+#include <stdio.h>
+
+DownloadManager::DownloadManager(QObject *parent)
+ : QObject(parent), downloadedCount(0), totalCount(0)
+{
+}
+
+void DownloadManager::append(const QStringList &urlList)
+{
+ foreach (QString url, urlList)
+ append(QUrl::fromEncoded(url.toLocal8Bit()));
+
+ if (downloadQueue.isEmpty())
+ QTimer::singleShot(0, this, SIGNAL(finished()));
+}
+
+void DownloadManager::append(const QUrl &url)
+{
+ if (downloadQueue.isEmpty())
+ QTimer::singleShot(0, this, SLOT(startNextDownload()));
+
+ downloadQueue.enqueue(url);
+ ++totalCount;
+}
+
+QString DownloadManager::saveFileName(const QUrl &url)
+{
+ QString path = url.path();
+ QString basename = QFileInfo(path).fileName();
+
+ if (basename.isEmpty())
+ basename = "download";
+
+ if (QFile::exists(basename)) {
+ // already exists, rename the old one
+ int i = 0;
+ while (QFile::exists(basename + ".old_" + QString::number(i)))
+ ++i;
+
+ QFile::rename(basename, basename + ".old_" + QString::number(i));
+ //basename += QString::number(i);
+ }
+
+ return basename;
+}
+
+void DownloadManager::startNextDownload()
+{
+ if (downloadQueue.isEmpty()) {
+ printf("%d/%d files downloaded successfully\n", downloadedCount, totalCount);
+ emit finished();
+ return;
+ }
+
+ QUrl url = downloadQueue.dequeue();
+
+ QString filename = saveFileName(url);
+ output.setFileName(filename);
+ if (!output.open(QIODevice::WriteOnly)) {
+ fprintf(stderr, "Problem opening save file '%s' for download '%s': %s\n",
+ qPrintable(filename), url.toEncoded().constData(),
+ qPrintable(output.errorString()));
+
+ startNextDownload();
+ return; // skip this download
+ }
+
+ QNetworkRequest request(url);
+ currentDownload = manager.get(request);
+ connect(currentDownload, SIGNAL(downloadProgress(qint64,qint64)),
+ SLOT(downloadProgress(qint64,qint64)));
+ connect(currentDownload, SIGNAL(finished()),
+ SLOT(downloadFinished()));
+ connect(currentDownload, SIGNAL(readyRead()),
+ SLOT(downloadReadyRead()));
+
+ // prepare the output
+ printf("Downloading %s...\n", url.toEncoded().constData());
+ downloadTime.start();
+}
+
+void DownloadManager::downloadProgress(qint64 bytesReceived, qint64 bytesTotal)
+{
+ progressBar.setStatus(bytesReceived, bytesTotal);
+
+ // calculate the download speed
+ double speed = bytesReceived * 1000.0 / downloadTime.elapsed();
+ QString unit;
+ if (speed < 1024) {
+ unit = "bytes/sec";
+ } else if (speed < 1024*1024) {
+ speed /= 1024;
+ unit = "kB/s";
+ } else {
+ speed /= 1024*1024;
+ unit = "MB/s";
+ }
+
+ progressBar.setMessage(QString::fromLatin1("%1 %2")
+ .arg(speed, 3, 'f', 1).arg(unit));
+ progressBar.update();
+}
+
+void DownloadManager::downloadFinished()
+{
+ progressBar.clear();
+ output.close();
+
+ if (currentDownload->error()) {
+ // download failed
+ fprintf(stderr, "Failed: %s\n", qPrintable(currentDownload->errorString()));
+ } else {
+ printf("Succeeded.\n");
+ ++downloadedCount;
+ }
+
+ currentDownload->deleteLater();
+ startNextDownload();
+}
+
+void DownloadManager::downloadReadyRead()
+{
+ output.write(currentDownload->readAll());
+}
diff --git a/tools/repogenfromonlinerepo/downloadmanager.h b/tools/repogenfromonlinerepo/downloadmanager.h
new file mode 100644
index 000000000..d6d1abd70
--- /dev/null
+++ b/tools/repogenfromonlinerepo/downloadmanager.h
@@ -0,0 +1,84 @@
+/****************************************************************************
+**
+** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the examples of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** You may use this file under the terms of the BSD license as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor
+** the names of its contributors may be used to endorse or promote
+** products derived from this software without specific prior written
+** permission.
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef DOWNLOADMANAGER_H
+#define DOWNLOADMANAGER_H
+
+#include <QFile>
+#include <QObject>
+#include <QQueue>
+#include <QTime>
+#include <QUrl>
+#include <QNetworkAccessManager>
+
+#include "textprogressbar.h"
+
+class DownloadManager: public QObject
+{
+ Q_OBJECT
+public:
+ DownloadManager(QObject *parent = 0);
+
+ void append(const QUrl &url);
+ void append(const QStringList &urlList);
+ QString saveFileName(const QUrl &url);
+
+signals:
+ void finished();
+
+private slots:
+ void startNextDownload();
+ void downloadProgress(qint64 bytesReceived, qint64 bytesTotal);
+ void downloadFinished();
+ void downloadReadyRead();
+
+private:
+ QNetworkAccessManager manager;
+ QQueue<QUrl> downloadQueue;
+ QNetworkReply *currentDownload;
+ QFile output;
+ QTime downloadTime;
+ TextProgressBar progressBar;
+
+ int downloadedCount;
+ int totalCount;
+};
+
+#endif
diff --git a/tools/repogenfromonlinerepo/main.cpp b/tools/repogenfromonlinerepo/main.cpp
new file mode 100644
index 000000000..b6a0db0c7
--- /dev/null
+++ b/tools/repogenfromonlinerepo/main.cpp
@@ -0,0 +1,306 @@
+/**************************************************************************
+**
+** This file is part of Qt SDK**
+**
+** Copyright (c) 2011 Nokia Corporation and/or its subsidiary(-ies).*
+**
+** Contact: Nokia Corporation qt-info@nokia.com**
+**
+** No Commercial Usage
+**
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+**
+** This file may be used under the terms of the GNU Lesser General Public
+** License version 2.1 as published by the Free Software Foundation and
+** appearing in the file LICENSE.LGPL included in the packaging of this file.
+** Please review the following information to ensure the GNU Lesser General
+** Public License version 2.1 requirements will be met:
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception version
+** 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you are unsure which license is appropriate for your use, please contact
+** (qt-info@nokia.com).
+**
+**************************************************************************/
+#include "downloadmanager.h"
+
+#include <QtCore/QCoreApplication>
+#include <QFile>
+#include <QString>
+#include <QDomDocument>
+#include <QDomElement>
+#include <QDomNodeList>
+#include <QStringList>
+#include <QDebug>
+#include <QFileInfo>
+#include <QDir>
+#include <iostream>
+
+static void printUsage()
+{
+ const QString appName = QFileInfo( QCoreApplication::applicationFilePath() ).fileName();
+ std::cout << "Usage: " << qPrintable(appName) << "--url <repository_url>" << std::endl;
+ std::cout << std::endl;
+ std::cout << "Example:" << std::endl;
+ std::cout << " " << qPrintable(appName) << " someDirectory foobar.7z" << std::endl;
+}
+
+
+int main(int argc, char *argv[])
+{
+ QCoreApplication app(argc, argv);
+
+ QString repoUrl = "http://www.forum.nokia.com/nokiaqtsdkrepository/oppdatering/windows/online_ndk_repo";
+
+ QStringList args = app.arguments();
+ for( QStringList::const_iterator it = args.constBegin(); it != args.constEnd(); ++it )
+ {
+ if( *it == QString::fromLatin1( "-h" ) || *it == QString::fromLatin1( "--help" ) )
+ {
+ printUsage();
+ return 0;
+ }
+ else if( *it == QString::fromLatin1( "-u" ) || *it == QString::fromLatin1( "--url" ) )
+ {
+ ++it;
+ if( it == args.end() ) {
+// printUsage();
+// return -1;
+ } else {
+ repoUrl = *it;
+ }
+ }
+ }
+
+ QEventLoop downloadEventLoop;
+
+ DownloadManager downloadManager;
+
+// get Updates.xml to get to know what we can download
+ downloadManager.append(QUrl(repoUrl + "/Updates.xml"));
+ QObject::connect( &downloadManager, SIGNAL( finished() ), &downloadEventLoop, SLOT( quit() ) );
+ downloadEventLoop.exec();
+// END - get Updates.xml to get to know what we can download
+
+ QFile batchFile("download.bat");
+ if (!batchFile.open(QIODevice::WriteOnly | QIODevice::Text)) {
+ qDebug() << "can not open " << QFileInfo(batchFile).absoluteFilePath();
+ return app.exec();
+ }
+
+ QTextStream batchFileOut(&batchFile);
+
+ const QString updatesXmlPath = "Updates.xml";
+
+ Q_ASSERT( !updatesXmlPath.isEmpty() );
+ Q_ASSERT( QFile::exists( updatesXmlPath ) );
+
+ QFile updatesFile( updatesXmlPath );
+ if ( !updatesFile.open( QIODevice::ReadOnly ) ) {
+ //qDebug() << QString( "Could not open Updates.xml for reading: %1").arg( updatesFile.errorString() ) ;
+ return app.exec();
+ }
+
+ QDomDocument doc;
+ QString err;
+ int line = 0;
+ int col = 0;
+ if ( !doc.setContent( &updatesFile, &err, &line, &col ) ) {
+ //qDebug() << QString( "Could not parse component index: %1:%2: %3").arg( QString::number( line ), QString::number( col ), err );
+ return app.exec();
+ }
+
+ const QDomElement root = doc.documentElement();
+ const QDomNodeList children = root.childNodes();
+ for ( int i = 0; i < children.count(); ++i ) {
+ //qDebug() << children.count();
+ QString packageName;
+ QString packageDisplayName;
+ QString packageDescription;
+ QString packageUpdateText;
+ QString packageVersion;
+ QString packageReleaseDate;
+ QString packageHash;
+ QString packageUserinterfacesAsString;
+ QString packageInstallPriority;
+ QString packageScript;
+ QString packageDependencies;
+ QString packageForcedInstallation;
+ bool packageIsVirtual = false;
+ QString sevenZString;
+ const QDomElement el = children.at( i ).toElement();
+ if ( el.isNull() )
+ continue;
+ if ( el.tagName() == QString("PackageUpdate") ) {
+ const QDomNodeList c2 = el.childNodes();
+
+ for ( int j = 0; j < c2.count(); ++j ) {
+ if ( c2.at( j ).toElement().tagName() == QString("Name") )
+ packageName = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("DisplayName") )
+ packageDisplayName = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("Description") )
+ packageDescription = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("UpdateText") )
+ packageUpdateText = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("Version") )
+ packageVersion = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("ReleaseDate") )
+ packageReleaseDate = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("SHA1") )
+ packageHash = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("UserInterfaces") )
+ packageUserinterfacesAsString = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("Script") )
+ packageScript = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("Dependencies") )
+ packageDependencies = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("ForcedInstallation") )
+ packageForcedInstallation = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("InstallPriority") )
+ packageInstallPriority = c2.at( j ).toElement().text();
+ else if ( c2.at( j ).toElement().tagName() == QString("Virtual") && c2.at( j ).toElement().text() == "true")
+ packageIsVirtual = true;
+ }
+ }
+ if (packageName.isEmpty()) {
+ continue;
+ }
+
+ if ( !packageScript.isEmpty() ) {
+ // get Updates.xml to get to know what we can download
+ downloadManager.append(QUrl(repoUrl + "/" + packageName + "/" + packageScript));
+ QObject::connect( &downloadManager, SIGNAL( finished() ), &downloadEventLoop, SLOT( quit() ) );
+ downloadEventLoop.exec();
+ // END - get Updates.xml to get to know what we can download
+
+ QString localScriptFileName = packageScript;
+ Q_ASSERT( QFile::exists( localScriptFileName ) );
+
+ QFile file(localScriptFileName);
+ if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
+ //qDebug() << localScriptFileName << " was not readable";
+ continue;
+ }
+
+ QTextStream in(&file);
+ while (!in.atEnd()) {
+ QString line = in.readLine();
+ if(line.contains(".7z")) {
+ int firstPosition = line.indexOf("\"");
+ QString subString = line.right(line.count() - firstPosition - 1); //-1 means "
+ //qDebug() << subString;
+ int secondPosition = subString.indexOf("\"");
+ sevenZString = subString.left(secondPosition);
+ //qDebug() << sevenZString;
+ break;
+ }
+ }
+ file.remove();
+ }
+ QStringList packageUserinterfaces = packageUserinterfacesAsString.split(",");
+ packageUserinterfaces.removeAll(QString());
+ packageUserinterfaces.removeAll("");
+
+ QStringList fileList;
+
+ //fileList << packageVersion + sevenZString;
+ foreach(const QString file, packageUserinterfaces) {
+ if(!file.isEmpty()) {
+ fileList << file;
+ }/* else {
+ qDebug() << "There is something wrong with the userinterface string list.";
+ return a.exec();
+ }*/
+ }
+ if(!packageScript.isEmpty()) {
+ fileList << packageScript;
+ }
+
+ QFile packagesXml( QString( QCoreApplication::applicationDirPath() + "/" + packageName + ".xml" ));
+ packagesXml.open( QIODevice::WriteOnly );
+ QTextStream packageAsXmlStream( &packagesXml );
+ packageAsXmlStream << QString( "<?xml version=\"1.0\"?>" ) << endl;
+ packageAsXmlStream << QString( "<Package>" ) << endl;
+ packageAsXmlStream << QString( " <DisplayName>%1</DisplayName>" ).arg(packageDisplayName) << endl;
+
+ if (!packageDescription.isEmpty()) {
+ packageAsXmlStream << QString( " <Description>%1</Description>" ).arg(packageDescription) << endl;
+ }
+
+ if (!packageUpdateText.isEmpty()) {
+ packageAsXmlStream << QString( " <UpdateText>%1</UpdateText>" ).arg(packageUpdateText) << endl;
+ }
+
+ if (!packageVersion.isEmpty()) {
+ packageAsXmlStream << QString( " <Version>%1</Version>" ).arg(packageVersion) << endl;
+ }
+
+ if (!packageReleaseDate.isEmpty()) {
+ packageAsXmlStream << QString( " <ReleaseDate>%1</ReleaseDate>" ).arg(packageReleaseDate) << endl;
+ }
+ packageAsXmlStream << QString( " <Name>%1</Name>" ).arg(packageName) << endl;
+
+ if (!packageScript.isEmpty()) {
+ packageAsXmlStream << QString( " <Script>%1</Script>" ).arg(packageScript) << endl;
+ }
+
+ if (packageIsVirtual) {
+ packageAsXmlStream << QString( " <Virtual>true</Virtual>" ) << endl;
+ }
+
+ if (!packageInstallPriority.isEmpty())
+ packageAsXmlStream << QString( " <InstallPriority>%1</InstallPriority>" ).arg(packageInstallPriority) << endl;
+
+ if (!packageDependencies.isEmpty())
+ packageAsXmlStream << QString( " <Dependencies>%1</Dependencies>" ).arg(packageDependencies) << endl;
+
+ if (!packageForcedInstallation.isEmpty())
+ packageAsXmlStream << QString( " <ForcedInstallation>%1</ForcedInstallation>" ).arg(packageForcedInstallation) << endl;
+
+ if (!packageUserinterfaces.isEmpty()) {
+ packageAsXmlStream << QString( " <UserInterfaces>" ) << endl;
+ foreach(const QString userInterfaceFile, packageUserinterfaces) {
+ packageAsXmlStream << QString( " <UserInterface>%1</UserInterface>" ).arg(userInterfaceFile) << endl;
+ }
+ packageAsXmlStream << QString( " </UserInterfaces>" ) << endl;
+ }
+ packageAsXmlStream << QString( "</Package>" ) << endl;
+
+ batchFileOut << "rem download line BEGIN =============================================\n";
+
+ batchFileOut << "mkdir " << packageName << "\\meta\n";
+ batchFileOut << "move " << QDir::toNativeSeparators(QFileInfo(packagesXml).absoluteFilePath()) << " " << packageName << "\\meta\\package.xml\n";
+ if (!sevenZString.isEmpty()) {
+ batchFileOut << "mkdir " << packageName << "\\data\n";
+ batchFileOut << "cd " << packageName << "\\data\n";
+ batchFileOut << "wget " << repoUrl << "/" << packageName << "/" << QString(packageVersion + sevenZString) << " -O " << sevenZString << "\n";
+ batchFileOut << "cd ..\\..\n";
+ }
+ batchFileOut << "cd " << packageName << "\\meta\n";
+ foreach(const QString file, fileList) {
+ batchFileOut << "wget " << repoUrl << "/" << packageName << "/" << file << "\n";
+ }
+ batchFileOut << "cd ..\\..\n";
+
+ batchFileOut << "rem download line END =============================================\n";
+ } //for ( int i = 0; i < children.count(); ++i ) {
+
+ if ( children.count() == 0 ) {
+ qDebug() << "no packages found";
+ return app.exec();
+ } else {
+ qDebug() << "found packages and wrote batch file";
+ }
+
+
+ return 0;
+}
diff --git a/tools/repogenfromonlinerepo/repogenfromonlinerepo.pro b/tools/repogenfromonlinerepo/repogenfromonlinerepo.pro
new file mode 100644
index 000000000..63bb503a4
--- /dev/null
+++ b/tools/repogenfromonlinerepo/repogenfromonlinerepo.pro
@@ -0,0 +1,16 @@
+QT += core network xml
+
+QT -= gui
+
+TARGET = repogenfromonlinerepo
+CONFIG += console
+CONFIG -= app_bundle
+
+TEMPLATE = app
+
+
+SOURCES += main.cpp
+HEADERS += downloadmanager.h
+SOURCES += downloadmanager.cpp
+HEADERS += textprogressbar.h
+SOURCES += textprogressbar.cpp
diff --git a/tools/repogenfromonlinerepo/textprogressbar.cpp b/tools/repogenfromonlinerepo/textprogressbar.cpp
new file mode 100644
index 000000000..ceba0922b
--- /dev/null
+++ b/tools/repogenfromonlinerepo/textprogressbar.cpp
@@ -0,0 +1,98 @@
+/****************************************************************************
+**
+** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the examples of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** You may use this file under the terms of the BSD license as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor
+** the names of its contributors may be used to endorse or promote
+** products derived from this software without specific prior written
+** permission.
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "textprogressbar.h"
+#include <QByteArray>
+#include <stdio.h>
+
+TextProgressBar::TextProgressBar()
+ : value(0), maximum(-1), iteration(0)
+{
+}
+
+void TextProgressBar::clear()
+{
+ printf("\n");
+ fflush(stdout);
+
+ iteration = 0;
+ value = 0;
+ maximum = -1;
+}
+
+void TextProgressBar::update()
+{
+ ++iteration;
+
+ if (maximum > 0) {
+ // we know the maximum
+ // draw a progress bar
+ int percent = value * 100 / maximum;
+ int hashes = percent / 2;
+
+ QByteArray progressbar(hashes, '#');
+ if (percent % 2)
+ progressbar += '>';
+
+ printf("\r[%-50s] %3d%% %s ",
+ progressbar.constData(),
+ percent,
+ qPrintable(message));
+ } else {
+ // we don't know the maximum, so we can't draw a progress bar
+ int center = (iteration % 48) + 1; // 50 spaces, minus 2
+ QByteArray before(qMax(center - 2, 0), ' ');
+ QByteArray after(qMin(center + 2, 50), ' ');
+
+ printf("\r[%s###%s] %s ",
+ before.constData(), after.constData(), qPrintable(message));
+ }
+}
+
+void TextProgressBar::setMessage(const QString &m)
+{
+ message = m;
+}
+
+void TextProgressBar::setStatus(qint64 val, qint64 max)
+{
+ value = val;
+ maximum = max;
+}
diff --git a/tools/repogenfromonlinerepo/textprogressbar.h b/tools/repogenfromonlinerepo/textprogressbar.h
new file mode 100644
index 000000000..91ea04dd1
--- /dev/null
+++ b/tools/repogenfromonlinerepo/textprogressbar.h
@@ -0,0 +1,63 @@
+/****************************************************************************
+**
+** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the examples of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** You may use this file under the terms of the BSD license as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor
+** the names of its contributors may be used to endorse or promote
+** products derived from this software without specific prior written
+** permission.
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef TEXTPROGRESSBAR_H
+#define TEXTPROGRESSBAR_H
+
+#include <QString>
+
+class TextProgressBar
+{
+public:
+ TextProgressBar();
+
+ void clear();
+ void update();
+ void setMessage(const QString &message);
+ void setStatus(qint64 value, qint64 maximum);
+
+private:
+ QString message;
+ qint64 value;
+ qint64 maximum;
+ int iteration;
+};
+
+#endif