понедельник, 11 ноября 2013 г.

Сокращение размера собственного инсталлятора Qt4 (компилятор MinGW)

Если вы собрали свой инсталлятор Qt4 для каких-то своих целей, то вероятно обратили внимание на то, что в каталоге сборки Qt в подкаталогах bin и lib лежат дублирующие друг друга наборы Qt библиотек - bin\QtCore4.dll, lib\QtCore4.dll и т.д. Если вы собирали Qt с флагом -debug-and-release, то один такой набор занимает порядка 500 Mb, то есть ваш инсталлятор установит лишние 500 Mb файлов, и сам будет больше на 50-60 "лишних" мегабайт. При использовании MinGW мы можем решить эту проблему никак не трогая проекта, который будет собираться напротив этой сборки Qt.

Сперва удаляем все Qt-шные dll из подкаталога lib. Библиотеки Qt теперь останутся только в подкаталоге bin.

При линковке вашего проекта, основанного на Qt, линкер будет искать библиотеки Qt именно в почищенном нами lib. Данную проблему можно решить заданием флагов QMAKE_LFLAGS в вашем проекте (QMAKE_LFLAGS += -L <ПУТЬ УСТАНОВКИ Qt>/bin), но решение с обёртками мне кажется более логичным. К тому же не забывайте, что разработчик не ожидает такого поведения от вашей сборки Qt. Для компилятора отличного от MinGW решение с QMAKE_LFLAGS может быть единственным. Чтобы решить эту проблему для сборки на основе MinGW мы можем создать файлы-обёртки для линкера.

Итак, чтобы создать обёртку для библиотеки QtCore4.dll нужно:
  1. Создать пустой файл libQtCore4.a в подкаталоге lib;
  2. Добавить в него текст GROUP(../bin/QtCore4.dll). Этой строкой вы укажете линкеру, что ему нужно добавить в список линковки библиотеку QtCore4.dll из каталога bin.
Теперь когда ваш проект будет линковаться с QtCore4, линкер откроет файл lib\libQtCore4.a, прочтёт скрипт, и подлинкует библиотеку bin\QtCore4.dll. Повторите эти действия для всех библиотек из вашей сборки Qt (QtCore4.dll, QtGui4.dll, QtSql4.dll и т.д.). Теперь ваш инсталлятор cможет похудеть на 50-60 Mb, а установленная Qt - приблизительно на 500.

воскресенье, 27 октября 2013 г.

Перемещение собранного Qt4

Как известно, во время сборки Qt4 в библиотеке QtCore и qmake сохраняется путь к каталогу сборки, например F:\qt4. Если вы переместите этот каталог в другое место, например, F:\toolchains\qt4, и попытаетесь использовать его как новый профиль в Qt Creator, то некоторые вещи откажутся работать - например, не будет грузиться sqlite плагин, т.к. программа будет искать его по старому пути в F:\qt4. Для этих целей существуют специальные программы-патчеры, которые изменяют пути внутри QtCore или qmake. Рассмотрим следующие варианты:
  • QtBinPatcher. Источник: 1. Позволяет патчить все необходимые файлы без указания каких-либо параметров командной строки. Наилучший вариант из виденных мной;
  • QtPathCorrector. Источник: 1 2. Позволяет патчить файл без указания старого пути. Требует задать новый путь через параметры командной строки. Например, зайдите в перемещённый каталог F:\toolchains\qt4 и выполните: qtpathcorrector patch -n "%cd%" -f bin\qmake.exe bin\QtCore4.dll lib\QtCore4.dll . Пути в qmake и QtCore установятся в "F:\toolchains\qt4". Недостатки: если возникли ошибки, то файл, который должен был быть исправлен, становится размером 0;
  • QPatch. Источник: 1. Требует задать как старый, так и новый путь через параметры командной строки. Недостатки: нужно указывать старый каталог, новый путь должен быть короче старого (что скорее всего неприемлимо для вас);
Теперь qmake будет знать, что prefix поменялся, и будет использовать новое значение. Чтобы проверить установился ли новый prefix, выполните команду qmake -query.

Встречаются заметки, что нужно также патчить пути в .prl файлах в каталоге lib (т.е. F:\toolchains\qt4\lib), но я не обнаружил ошибок или неправильного поведения или компиляции своих программ, если эти пути оставить как есть при использовании патчера, которому нужно в явном виде указывать какие файлы патчить.

    вторник, 11 июня 2013 г.

    Использование ссылок svn+ssh:// на SourceForge

    Если вы используете svn репозиторий на sourceforge.net, TortoiseSVN на локальном компьютере, и репозиторий по протоколу svn+ssh://, то вы можете столкнуться с тем, что commit или checkout проваливается:

    svn: E720087: Can't create tunnel: Параметр задан неверно.

    Это связано с тем, что у вас в PATH отсутствует совместимая версия plink.exe. Чтобы исправить эту ситуацию, можно указать TortoiseSVN использовать свою собственную версию plink-a. Для этого создайте переменную окружения SVN_SSH с таким содержимым:

    C:/Program Files/TortoiseSVN/bin/TortoisePlink.exe

    Не забудьте указать правильный каталог, где установлен TortoiseSVN. Если же вы используете SSH ключи для авторизации, то эта переменная будет выглядеть так:

    "C:/Program Files/TortoiseSVN/bin/TortoisePlink.exe" -i ПУТЬ_К_PRIVATE_КЛЮЧУ
    Ссылки:

    понедельник, 10 июня 2013 г.

    Медленная инициализация SSL в Qt на Windows

    Если вы пишете сетевое приложение с помощью Qt и уже подложили SSL библиотеки в каталог с программой, и ваша программа успешно скачивает секретные данные по протоколу https, то вы могли заметить довольно медленную инициализацию приложения на Windows.

    Если раньше ваша программа стартовала и начинала скачивание данных по http за 200 мс., то теперь с https это время увеличилось до 800 мс. (и это на Phenom II X6)! Задержка происходит в методе QNetworkAccessManager::get(). Использовав профайлер AQTime я выяснил, что основная задержка была внутри модуля QtNetwork в функции q_RAND_status(). После гугления стало ясно, что SSL инфраструктуру в программе лучше инициализировать чем раньше тем лучше, и это связано с кучей (heap) приложения.

    Если ещё до создания объекта QApplication добавить следующий простой код, то инициализация программы сократится с 800 мс до 400 мс.:
    int main(int argc, char *argv[])
    {
        qDebug(QSslSocket::supportsSsl()
                   ? "SSL is supported"
                   : "SSL is not supported");
    
        QApplication app(argc, argv);
    
    ...
    Ссылки:

    ld.exe: final link failed: Memory exhausted

    Если вы компилируете Qt самостоятельно с помощью MinGW и на сборке debug версии получаете ошибку "ld.exe: final link failed: Memory exhausted", то используйте для компиляции платформу win32-g++-4.6:

    configure.exe -platform win32-g++-4.6 ...

    Данный mkspec добавляет новые ключи компиляции, которые убирают из dll много мусора, и линковка должна пройти успешно. Сам компилятор GCC при этом должен быть версии 4.6 или выше.

    пятница, 18 января 2013 г.

    Установщик Qt Linguist 4.8.4 для Windows

    Qt Linguist - средство локализации программ. Поддерживает файлы переводов в форматах Qt (.ts), XLIFF (.xlf) и GNU Gettext (.po).

    Ссылки: