#include "s60devices.h" #include #include #include #include namespace { const char * const SYMBIAN_SDKS_KEY = "HKEY_LOCAL_MACHINE\\Software\\Symbian\\EPOC SDKs"; const char * const SYMBIAN_PATH_KEY = "CommonPath"; const char * const SYMBIAN_DEVICES_FILE = "devices.xml"; const char * const DEVICES_LIST = "devices"; const char * const DEVICE = "device"; const char * const DEVICE_ID = "id"; const char * const DEVICE_NAME = "name"; const char * const DEVICE_DEFAULT = "default"; const char * const DEVICE_EPOCROOT = "epocroot"; const char * const DEVICE_TOOLSROOT = "toolsroot"; } using namespace Qt4ProjectManager::Internal; S60Devices::S60Devices(QObject *parent) : QObject(parent) { } bool S60Devices::read() { m_devices.clear(); m_errorString = QString(); // Check the windows registry via QSettings for devices.xml path QSettings settings(SYMBIAN_SDKS_KEY, QSettings::NativeFormat); QString devicesXmlPath = settings.value(SYMBIAN_PATH_KEY).toString(); if (devicesXmlPath.isEmpty()) { m_errorString = "Could not find installed SDKs in registry."; return false; } devicesXmlPath += QLatin1String("/") + QLatin1String(SYMBIAN_DEVICES_FILE); QFile devicesFile(devicesXmlPath); if (!devicesFile.open(QIODevice::ReadOnly)) { m_errorString = QString("Could not read devices file at %1.").arg(devicesXmlPath); return false; } QXmlStreamReader xml(&devicesFile); while (!xml.atEnd()) { xml.readNext(); if (xml.isStartElement() && xml.name() == DEVICES_LIST) { if (xml.attributes().value("version") == "1.0") { // Look for correct device while (!(xml.isEndElement() && xml.name() == DEVICES_LIST) && !xml.atEnd()) { xml.readNext(); if (xml.isStartElement() && xml.name() == DEVICE) { Device device; device.id = xml.attributes().value(DEVICE_ID).toString(); device.name = xml.attributes().value(DEVICE_NAME).toString(); if (xml.attributes().value(DEVICE_DEFAULT).toString() == "yes") device.isDefault = true; else device.isDefault = false; while (!(xml.isEndElement() && xml.name() == DEVICE) && !xml.atEnd()) { xml.readNext(); if (xml.isStartElement() && xml.name() == DEVICE_EPOCROOT) { device.epocRoot = xml.readElementText(); } else if (xml.isStartElement() && xml.name() == DEVICE_TOOLSROOT) { device.toolsRoot = xml.readElementText(); } } m_devices.append(device); } } } else { xml.raiseError("Invalid 'devices' element version."); } } } devicesFile.close(); if (xml.hasError()) { m_errorString = xml.errorString(); return false; } return true; } bool S60Devices::detectQtForDevices() { for (int i = 0; i < m_devices.size(); ++i) { QFile qtDll(QString("%1/epoc32/release/winscw/udeb/QtCore.dll").arg(m_devices[i].epocRoot)); if (!qtDll.exists() || !qtDll.open(QIODevice::ReadOnly)) { m_devices[i].qt = QString(); continue; } const QString indicator = "\\src\\corelib\\kernel\\qobject.h"; int indicatorlength = indicator.length(); QByteArray buffer; QByteArray previousBuffer; int index = -1; while (!qtDll.atEnd()) { buffer = qtDll.read(10000); index = buffer.indexOf(indicator.toLatin1()); if (index >= 0) break; if (!qtDll.atEnd()) qtDll.seek(qtDll.pos()-indicatorlength); previousBuffer = buffer; } int lastIndex = index; while (index >= 0 && buffer.at(index)) --index; if (index < 0) { // this is untested } else { index += 2; // the 0 and another byte for some reason m_devices[i].qt = QDir::toNativeSeparators(buffer.mid(index, lastIndex-index)); } qtDll.close(); } return true; } QString S60Devices::errorString() const { return m_errorString; } QList S60Devices::devices() const { return m_devices; } S60Devices::Device S60Devices::deviceForRoot(const QString &epocRoot) const { foreach (const S60Devices::Device &i, m_devices) { if (i.epocRoot == epocRoot) { return i; } } return Device(); }