2010-08-07 09:10:44 -04:00
|
|
|
/*
|
|
|
|
* Copyright (C) 2010 Felix Geyer <debfx@fobos.de>
|
|
|
|
*
|
|
|
|
* This program is free software: you can redistribute it and/or modify
|
|
|
|
* it under the terms of the GNU General Public License as published by
|
|
|
|
* the Free Software Foundation, either version 2 or (at your option)
|
|
|
|
* version 3 of the License.
|
|
|
|
*
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include "Parser.h"
|
|
|
|
|
|
|
|
#include <QtCore/QFile>
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
#include "Database.h"
|
|
|
|
#include "Metadata.h"
|
|
|
|
|
2010-08-07 09:10:44 -04:00
|
|
|
Parser::Parser(Database* db)
|
|
|
|
{
|
|
|
|
m_db = db;
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta = db->metadata();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
bool Parser::parse(const QString& filename)
|
|
|
|
{
|
|
|
|
QFile file(filename);
|
|
|
|
file.open(QIODevice::ReadOnly | QIODevice::Text);
|
|
|
|
m_xml.setDevice(&file);
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
m_tmpParent = new Group();
|
2010-08-07 09:10:44 -04:00
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
if (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "KeePassFile") {
|
|
|
|
parseKeePassFile();
|
|
|
|
}
|
|
|
|
else {
|
2010-08-12 15:38:59 -04:00
|
|
|
raiseError();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
if (!m_tmpParent->children().isEmpty()) {
|
|
|
|
delete m_tmpParent;
|
|
|
|
raiseError();
|
|
|
|
}
|
|
|
|
|
2010-08-07 09:10:44 -04:00
|
|
|
return !m_xml.error();
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseKeePassFile()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "KeePassFile");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Meta") {
|
|
|
|
parseMeta();
|
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Root") {
|
|
|
|
parseRoot();
|
|
|
|
}
|
|
|
|
else {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_xml.skipCurrentElement();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseMeta()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Meta");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Generator") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setGenerator(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DatabaseName") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setName(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DatabaseNameChanged") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setNameChanged(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DatabaseDescription") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setDescription(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DatabaseDescriptionChanged") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setDescriptionChanged(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DefaultUserName") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setDefaultUserName(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DefaultUserNameChanged") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setDefaultUserNameChanged(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "MaintenanceHistoryDays") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setMaintenanceHistoryDays(readNumber());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "MemoryProtection") {
|
|
|
|
parseMemoryProtection();
|
|
|
|
}
|
|
|
|
else if (m_xml.name() == "CustomIcons") {
|
|
|
|
parseCustomIcons();
|
|
|
|
}
|
|
|
|
else if (m_xml.name() == "RecycleBinEnabled") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setRecycleBinEnabled(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "RecycleBinUUID") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setRecycleBinUuid(readUuid());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "RecycleBinChanged") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setRecycleBinChanged(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "EntryTemplatesGroup") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setEntryTemplatesGroup(readUuid());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "EntryTemplatesGroupChanged") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setEntryTemplatesGroupChanged(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "LastSelectedGroup") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setLastSelectedGroup(readUuid());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "LastTopVisibleGroup") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setLastTopVisibleGroup(readUuid());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "CustomData") {
|
|
|
|
parseCustomData();
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseMemoryProtection()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "MemoryProtection");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "ProtectTitle") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setProtectTitle(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "ProtectUserName") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setProtectUsername(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "ProtectPassword") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setProtectPassword(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "ProtectURL") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setProtectUrl(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "ProtectNotes") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setProtectNotes(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "AutoEnableVisualHiding") {
|
2010-08-12 15:38:59 -04:00
|
|
|
m_meta->setAutoEnableVisualHiding(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseCustomIcons()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "CustomIcons");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Icon") {
|
|
|
|
parseIcon();
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseIcon()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Icon");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
Uuid uuid;
|
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "UUID") {
|
2010-08-12 15:38:59 -04:00
|
|
|
uuid = readUuid();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Data") {
|
2010-08-12 15:38:59 -04:00
|
|
|
QImage image;
|
|
|
|
image.loadFromData(readBinary());
|
|
|
|
m_meta->addCustomIcon(uuid, image);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseCustomData()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "CustomData");
|
|
|
|
|
|
|
|
// TODO
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseRoot()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Root");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Group") {
|
2010-08-12 15:38:59 -04:00
|
|
|
Group* rootGroup = parseGroup();
|
2010-08-12 15:43:57 -04:00
|
|
|
if (rootGroup) {
|
2010-08-12 15:38:59 -04:00
|
|
|
rootGroup->setParent(m_db);
|
|
|
|
}
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DeletedObjects") {
|
2010-08-12 15:38:59 -04:00
|
|
|
// TODO implement
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
Group* Parser::parseGroup()
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Group");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
Group* group = 0;
|
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "UUID") {
|
2010-08-12 15:38:59 -04:00
|
|
|
Uuid uuid = readUuid();
|
|
|
|
if (uuid.isNull()) {
|
|
|
|
raiseError();
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
group = getGroup(uuid);
|
|
|
|
}
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Name") {
|
2010-08-12 15:38:59 -04:00
|
|
|
group->setName(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Notes") {
|
2010-08-12 15:38:59 -04:00
|
|
|
group->setNotes(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "IconID") {
|
2010-08-12 15:38:59 -04:00
|
|
|
int iconId = readNumber();
|
|
|
|
if (iconId != 0)
|
|
|
|
group->setIcon(iconId);
|
|
|
|
}
|
|
|
|
else if (m_xml.name() == "CustomIconUUID") {
|
|
|
|
Uuid uuid = readUuid();
|
|
|
|
if (!uuid.isNull()) {
|
|
|
|
group->setIcon(uuid);
|
|
|
|
}
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Times") {
|
2010-08-12 15:38:59 -04:00
|
|
|
group->setTimeInfo(parseTimes());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "IsExpanded") {
|
2010-08-12 15:38:59 -04:00
|
|
|
group->setExpanded(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DefaultAutoTypeSequence") {
|
2010-08-12 15:38:59 -04:00
|
|
|
group->setDefaultAutoTypeSequence(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "EnableAutoType") {
|
2010-08-12 15:38:59 -04:00
|
|
|
// TODO implement
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "EnableSearching") {
|
2010-08-12 15:38:59 -04:00
|
|
|
// TODO implement
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "LastTopVisibleEntry") {
|
2010-08-12 15:38:59 -04:00
|
|
|
Uuid uuid = readUuid();
|
|
|
|
if (uuid.isNull())
|
|
|
|
group->setLastTopVisibleEntry(0);
|
|
|
|
else
|
|
|
|
group->setLastTopVisibleEntry(getEntry(uuid));
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Group") {
|
2010-08-12 15:38:59 -04:00
|
|
|
Group* newGroup = parseGroup();
|
|
|
|
if (newGroup) {
|
|
|
|
newGroup->setParent(group);
|
|
|
|
}
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Entry") {
|
2010-08-12 15:38:59 -04:00
|
|
|
Entry* newEntry = parseEntry();
|
|
|
|
if (newEntry) {
|
|
|
|
newEntry->setGroup(group);
|
|
|
|
}
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
2010-08-12 15:38:59 -04:00
|
|
|
|
|
|
|
return group;
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
Entry* Parser::parseEntry()
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Entry");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
Entry* entry = 0;
|
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "UUID") {
|
2010-08-12 15:38:59 -04:00
|
|
|
Uuid uuid = readUuid();
|
|
|
|
if (uuid.isNull()) {
|
|
|
|
raiseError();
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
entry = getEntry(uuid);
|
|
|
|
}
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "IconID") {
|
2010-08-12 15:38:59 -04:00
|
|
|
int iconId = readNumber();
|
|
|
|
if (iconId != 0)
|
|
|
|
entry->setIcon(iconId);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "CustomIconUUID") {
|
2010-08-12 15:38:59 -04:00
|
|
|
Uuid uuid = readUuid();
|
|
|
|
if (!uuid.isNull())
|
|
|
|
entry->setIcon(uuid);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "ForegroundColor") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->setForegroundColor(readColor());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "BackgroundColor") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->setBackgroundColor(readColor());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "OverrideURL") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->setOverrideUrl(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Times") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->setTimeInfo(parseTimes());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "String") {
|
2010-08-12 15:38:59 -04:00
|
|
|
parseEntryString(entry);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Binary") {
|
2010-08-12 15:38:59 -04:00
|
|
|
parseEntryBinary(entry);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "AutoType") {
|
2010-08-12 15:38:59 -04:00
|
|
|
parseAutoType(entry);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "History") {
|
|
|
|
parseEntryHistory();
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
void Parser::parseEntryString(Entry *entry)
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "String");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
QString key;
|
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Key") {
|
2010-08-12 15:38:59 -04:00
|
|
|
key = readString();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Value") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->addAttribute(key, readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
void Parser::parseEntryBinary(Entry *entry)
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Binary");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
QString key;
|
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Key") {
|
2010-08-12 15:38:59 -04:00
|
|
|
key = readString();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Value") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->addAttachment(key, readBinary());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
void Parser::parseAutoType(Entry* entry)
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "AutoType");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Enabled") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->setAutoTypeEnabled(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DataTransferObfuscation") {
|
2010-08-12 15:38:59 -04:00
|
|
|
entry->setAutoTypeObfuscation(readNumber());
|
|
|
|
}
|
|
|
|
else if (m_xml.name() == "DefaultSequence") {
|
|
|
|
entry->setDefaultAutoTypeSequence(readString());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Association") {
|
2010-08-12 15:38:59 -04:00
|
|
|
parseAutoTypeAssoc(entry);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
void Parser::parseAutoTypeAssoc(Entry *entry)
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Association");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
AutoTypeAssociation assoc;
|
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Window") {
|
2010-08-12 15:38:59 -04:00
|
|
|
assoc.window = readString();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "KeystrokeSequence") {
|
2010-08-12 15:38:59 -04:00
|
|
|
assoc.sequence = readString();
|
|
|
|
entry->addAutoTypeAssociation(assoc);
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::parseEntryHistory()
|
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "History");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "Entry") {
|
2010-08-12 15:38:59 -04:00
|
|
|
// TODO implement
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
TimeInfo Parser::parseTimes()
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
|
|
|
Q_ASSERT(m_xml.isStartElement() && m_xml.name() == "Times");
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
TimeInfo timeInfo;
|
|
|
|
while (!m_xml.error() && m_xml.readNextStartElement()) {
|
2010-08-07 09:10:44 -04:00
|
|
|
if (m_xml.name() == "LastModificationTime") {
|
2010-08-12 15:38:59 -04:00
|
|
|
timeInfo.setLastModificationTime(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "CreationTime") {
|
2010-08-12 15:38:59 -04:00
|
|
|
timeInfo.setCreationTime(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "LastAccessTime") {
|
2010-08-12 15:38:59 -04:00
|
|
|
timeInfo.setLastAccessTime(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "ExpiryTime") {
|
2010-08-12 15:38:59 -04:00
|
|
|
timeInfo.setExpiryTime(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "Expires") {
|
2010-08-12 15:38:59 -04:00
|
|
|
timeInfo.setExpires(readBool());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "UsageCount") {
|
2010-08-12 15:38:59 -04:00
|
|
|
timeInfo.setUsageCount(readNumber());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else if (m_xml.name() == "LocationChanged") {
|
2010-08-12 15:38:59 -04:00
|
|
|
timeInfo.setLocationChanged(readDateTime());
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
m_xml.skipCurrentElement();
|
|
|
|
}
|
|
|
|
}
|
2010-08-12 15:38:59 -04:00
|
|
|
|
|
|
|
return timeInfo;
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
QString Parser::readString()
|
|
|
|
{
|
|
|
|
return m_xml.readElementText();
|
|
|
|
}
|
|
|
|
|
|
|
|
bool Parser::readBool()
|
|
|
|
{
|
|
|
|
QString str = readString();
|
|
|
|
|
|
|
|
if (str == "True") {
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
else if (str == "False") {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
else {
|
2010-08-12 15:38:59 -04:00
|
|
|
raiseError();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
QDateTime Parser::readDateTime()
|
|
|
|
{
|
|
|
|
QString str = readString();
|
|
|
|
QDateTime dt = QDateTime::fromString(str, Qt::ISODate);
|
|
|
|
|
|
|
|
if (!dt.isValid()) {
|
2010-08-12 15:38:59 -04:00
|
|
|
raiseError();
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
return dt;
|
|
|
|
}
|
|
|
|
|
2010-08-12 15:38:59 -04:00
|
|
|
QColor Parser::readColor()
|
2010-08-07 09:10:44 -04:00
|
|
|
{
|
2010-08-12 15:38:59 -04:00
|
|
|
QString colorStr = readString();
|
|
|
|
if (colorStr.length() != 7 || colorStr[0] != '#') {
|
|
|
|
raiseError();
|
|
|
|
return QColor();
|
|
|
|
}
|
|
|
|
|
|
|
|
QColor color;
|
|
|
|
for (int i=0; i<= 2; i++) {
|
|
|
|
QString rgbPartStr = colorStr.mid(1 + 2*i, 2);
|
|
|
|
bool ok;
|
|
|
|
int rgbPart = rgbPartStr.toInt(&ok);
|
|
|
|
if (!ok || rgbPart > 255) {
|
|
|
|
raiseError();
|
|
|
|
return QColor();
|
|
|
|
}
|
|
|
|
|
|
|
|
if (i == 0) {
|
|
|
|
color.setRed(rgbPart);
|
|
|
|
}
|
|
|
|
else if (i == 1) {
|
|
|
|
color.setGreen(rgbPart);
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
color.setBlue(rgbPart);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return color;
|
|
|
|
}
|
|
|
|
|
|
|
|
int Parser::readNumber()
|
|
|
|
{
|
|
|
|
bool ok;
|
|
|
|
int result = readString().toInt(&ok);
|
|
|
|
if (!ok) {
|
|
|
|
raiseError();
|
|
|
|
}
|
|
|
|
return result;
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
Uuid Parser::readUuid()
|
|
|
|
{
|
2010-08-12 15:38:59 -04:00
|
|
|
QByteArray uuidBin = readBinary();
|
|
|
|
if (uuidBin.length() != Uuid::length) {
|
|
|
|
raiseError();
|
|
|
|
return Uuid();
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
return Uuid(readBinary());
|
|
|
|
}
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
QByteArray Parser::readBinary()
|
|
|
|
{
|
2010-08-12 15:38:59 -04:00
|
|
|
return QByteArray::fromBase64(readString().toAscii());
|
|
|
|
}
|
|
|
|
|
|
|
|
Group* Parser::getGroup(const Uuid& uuid)
|
|
|
|
{
|
|
|
|
Q_FOREACH (Group* group, m_groups) {
|
|
|
|
if (group->uuid() == uuid) {
|
|
|
|
return group;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
Group* group = new Group();
|
|
|
|
group->setUuid(uuid);
|
|
|
|
group->setParent(m_tmpParent);
|
|
|
|
m_groups << group;
|
|
|
|
return group;
|
|
|
|
}
|
|
|
|
|
|
|
|
Entry* Parser::getEntry(const Uuid& uuid)
|
|
|
|
{
|
|
|
|
Q_FOREACH (Entry* entry, m_entries) {
|
|
|
|
if (entry->uuid() == uuid) {
|
|
|
|
return entry;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
Entry* entry = new Entry();
|
|
|
|
entry->setUuid(uuid);
|
|
|
|
entry->setGroup(m_tmpParent);
|
|
|
|
m_entries << entry;
|
|
|
|
return entry;
|
|
|
|
}
|
|
|
|
|
|
|
|
void Parser::raiseError()
|
|
|
|
{
|
|
|
|
m_xml.raiseError(tr("Invalid database file"));
|
2010-08-07 09:10:44 -04:00
|
|
|
}
|