1 /****************************************************************************
2 **
3 ** Copyright (C) 2015 The Qt Company Ltd.
4 ** Contact: http://www.qt.io/licensing/
5 **
6 ** This file is part of the Qt Assistant of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and The Qt Company. For licensing terms
14 ** and conditions see http://www.qt.io/terms-conditions. For further
15 ** information use the contact form at http://www.qt.io/contact-us.
16 **
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 2.1 or version 3 as published by the Free
20 ** Software Foundation and appearing in the file LICENSE.LGPLv21 and
21 ** LICENSE.LGPLv3 included in the packaging of this file. Please review the
22 ** following information to ensure the GNU Lesser General Public License
23 ** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
24 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
25 **
26 ** As a special exception, The Qt Company gives you certain additional
27 ** rights. These rights are described in The Qt Company LGPL Exception
28 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
29 **
30 ** GNU General Public License Usage
31 ** Alternatively, this file may be used under the terms of the GNU
32 ** General Public License version 3.0 as published by the Free Software
33 ** Foundation and appearing in the file LICENSE.GPL included in the
34 ** packaging of this file.  Please review the following information to
35 ** ensure the GNU General Public License version 3.0 requirements will be
36 ** met: http://www.gnu.org/copyleft/gpl.html.
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41 
42 #include <QRegExp>
43 
44 #include "adpreader.h"
45 
versionIsAtLeast320(const QString & version)46 static bool versionIsAtLeast320(const QString &version)
47 {
48     return QRegExp("\\d.\\d\\.\\d").exactMatch(version)
49             && (version[0] > '3' || (version[0] == '3' && version[2] >= '2'));
50 }
51 
52 QT_BEGIN_NAMESPACE
53 
readData(const QByteArray & contents)54 void AdpReader::readData(const QByteArray &contents)
55 {
56     clear();
57     m_contents.clear();
58     m_keywords.clear();
59     m_properties.clear();
60     m_files.clear();
61     addData(contents);
62     while (!atEnd()) {
63         readNext();
64         if (isStartElement()) {
65             if (name().toString().toLower() == QLatin1String("assistantconfig")
66                 && versionIsAtLeast320(attributes().value(QLatin1String("version")).toString())) {
67                 readProject();
68             } else if (name().toString().toLower() == QLatin1String("dcf")) {
69                 QString ref = attributes().value(QLatin1String("ref")).toString();
70                 addFile(ref);
71                 m_contents.append(ContentItem(attributes().value(QLatin1String("title")).toString(),
72                     ref, 0));
73                 readDCF();
74             } else {
75                 raiseError();
76             }
77         }
78     }
79 }
80 
contents() const81 QList<ContentItem> AdpReader::contents() const
82 {
83     return m_contents;
84 }
85 
keywords() const86 QList<KeywordItem> AdpReader::keywords() const
87 {
88     return m_keywords;
89 }
90 
files() const91 QSet<QString> AdpReader::files() const
92 {
93     return m_files;
94 }
95 
properties() const96 QMap<QString, QString> AdpReader::properties() const
97 {
98     return m_properties;
99 }
100 
readProject()101 void AdpReader::readProject()
102 {
103     while (!atEnd()) {
104         readNext();
105         if (isStartElement()) {
106             QString s = name().toString().toLower();
107             if (s == QLatin1String("profile")) {
108                 readProfile();
109             } else if (s == QLatin1String("dcf")) {
110                 QString ref = attributes().value(QLatin1String("ref")).toString();
111                 addFile(ref);
112                 m_contents.append(ContentItem(attributes().value(QLatin1String("title")).toString(),
113                     ref, 0));
114                 readDCF();
115             } else {
116                 raiseError();
117             }
118         }
119     }
120 }
121 
readProfile()122 void AdpReader::readProfile()
123 {
124     while (!atEnd()) {
125         readNext();
126         if (isStartElement()) {
127             if (name().toString().toLower() == QLatin1String("property")) {
128                 QString prop = attributes().value(QLatin1String("name")).toString().toLower();
129                 m_properties[prop] = readElementText();
130             } else {
131                 raiseError();
132             }
133         } else if (isEndElement()) {
134             break;
135         }
136     }
137 }
138 
readDCF()139 void AdpReader::readDCF()
140 {
141     int depth = 0;
142     while (!atEnd()) {
143         readNext();
144         QString str = name().toString().toLower();
145         if (isStartElement()) {
146             if (str == QLatin1String("section")) {
147                 QString ref = attributes().value(QLatin1String("ref")).toString();
148                 addFile(ref);
149                 m_contents.append(ContentItem(attributes().value(QLatin1String("title")).toString(),
150                     ref, ++depth));
151             } else if (str == QLatin1String("keyword")) {
152                 QString ref = attributes().value(QLatin1String("ref")).toString();
153                 addFile(ref);
154                 m_keywords.append(KeywordItem(readElementText(), ref));
155             } else {
156                 raiseError();
157             }
158         } else if (isEndElement()) {
159             if (str == QLatin1String("section"))
160                 --depth;
161             else if (str == QLatin1String("dcf"))
162                 break;
163         }
164     }
165 }
166 
addFile(const QString & file)167 void AdpReader::addFile(const QString &file)
168 {
169     QString s = file;
170     if (s.startsWith(QLatin1String("./")))
171         s = s.mid(2);
172     int i = s.indexOf(QLatin1Char('#'));
173     if (i > -1)
174         s = s.left(i);
175     if (!m_files.contains(s))
176         m_files.insert(s);
177 }
178 
179 QT_END_NAMESPACE
180