1 | /**************************************************************************** |
2 | ** |
3 | ** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies). |
4 | ** Contact: http://www.qt-project.org/legal |
5 | ** |
6 | ** This file is part of the QtDBus module 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 Digia. For licensing terms and |
14 | ** conditions see http://qt.digia.com/licensing. For further information |
15 | ** use the contact form at http://qt.digia.com/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 as published by the Free Software |
20 | ** Foundation and appearing in the file LICENSE.LGPL included in the |
21 | ** packaging of this file. Please review the following information to |
22 | ** ensure the GNU Lesser General Public License version 2.1 requirements |
23 | ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. |
24 | ** |
25 | ** In addition, as a special exception, Digia gives you certain additional |
26 | ** rights. These rights are described in the Digia Qt LGPL Exception |
27 | ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. |
28 | ** |
29 | ** GNU General Public License Usage |
30 | ** Alternatively, this file may be used under the terms of the GNU |
31 | ** General Public License version 3.0 as published by the Free Software |
32 | ** Foundation and appearing in the file LICENSE.GPL included in the |
33 | ** packaging of this file. Please review the following information to |
34 | ** ensure the GNU General Public License version 3.0 requirements will be |
35 | ** met: http://www.gnu.org/copyleft/gpl.html. |
36 | ** |
37 | ** |
38 | ** $QT_END_LICENSE$ |
39 | ** |
40 | ****************************************************************************/ |
41 | |
42 | #include "qdbusintrospection_p.h" |
43 | #include "qdbusxmlparser_p.h" |
44 | |
45 | #ifndef QT_NO_DBUS |
46 | |
47 | QT_BEGIN_NAMESPACE |
48 | |
49 | /*! |
50 | \class QDBusIntrospection |
51 | \brief Information about introspected objects and interfaces on D-Bus. |
52 | \internal |
53 | |
54 | This class provides structures and methods for parsing the XML introspection data for D-Bus. |
55 | Normally, you don't have to use the methods provided here: QDBusInterface and QDBusObject will |
56 | do that for you. |
57 | |
58 | But they may prove useful if the XML data was obtained through other means (like parsing a file). |
59 | */ |
60 | |
61 | /*! |
62 | \class QDBusIntrospection::Argument |
63 | \brief One argument to a D-Bus method or signal. |
64 | |
65 | This struct represents one argument passed to a method or received from a method or signal in |
66 | D-Bus. The struct does not contain information on the direction (input or output). |
67 | */ |
68 | |
69 | /*! |
70 | \variable QDBusIntrospection::Argument::type |
71 | The argument type. |
72 | */ |
73 | |
74 | /*! |
75 | \variable QDBusIntrospection::Argument::name |
76 | The argument name. The argument name is optional, so this may be a null QString. |
77 | */ |
78 | |
79 | /*! |
80 | \fn QDBusIntrospection::Argument::operator==(const Argument &other) const |
81 | Compares this object against \a other and return true if they are the same. |
82 | */ |
83 | |
84 | /*! |
85 | \class QDBusIntrospection::Method |
86 | \brief Information about one method. |
87 | |
88 | This struct represents one method discovered through introspection. A method is composed of |
89 | its \a name, its input arguments, its output arguments, and, optionally, annotations. There are no |
90 | "in-out" arguments. |
91 | */ |
92 | |
93 | /*! |
94 | \variable QDBusIntrospection::Method::name |
95 | The method's name. |
96 | */ |
97 | |
98 | /*! |
99 | \variable QDBusIntrospection::Method::inputArgs |
100 | A list of the method's input arguments. |
101 | */ |
102 | |
103 | /*! |
104 | \variable QDBusIntrospection::Method::outputArgs |
105 | A list of the method's output arguments (i.e., return values). |
106 | */ |
107 | |
108 | /*! |
109 | \variable QDBusIntrospection::Method::annotations |
110 | The annotations associated with the method. Each annotation is a pair of strings, where the key |
111 | is of the same format as a D-Bus interface name. The value is arbitrary. |
112 | */ |
113 | |
114 | /*! |
115 | \fn QDBusIntrospection::Method::operator==(const Method &other) const |
116 | Compares this object against \a other and return true if they are the same. |
117 | */ |
118 | |
119 | /*! |
120 | \class QDBusIntrospection::Signal |
121 | \brief Information about one signal. |
122 | |
123 | This struct represents one signal discovered through introspection. A signal is composed of |
124 | its \a name, its output arguments, and, optionally, annotations. |
125 | */ |
126 | |
127 | /*! |
128 | \variable QDBusIntrospection::Signal::name |
129 | The signal's name. |
130 | */ |
131 | |
132 | /*! |
133 | \variable QDBusIntrospection::Signal::outputArgs |
134 | A list of the signal's arguments. |
135 | */ |
136 | |
137 | /*! |
138 | \variable QDBusIntrospection::Signal::annotations |
139 | The annotations associated with the signal. Each annotation is a pair of strings, where the key |
140 | is of the same format as a D-Bus interface name. The value is arbitrary. |
141 | */ |
142 | |
143 | /*! |
144 | \fn QDBusIntrospection::Signal::operator==(const Signal& other) const |
145 | Compares this object against \a other and return true if they are the same. |
146 | */ |
147 | |
148 | /*! |
149 | \class QDBusIntrospection::Property |
150 | \brief Information about one property. |
151 | |
152 | This struct represents one property discovered through introspection. A property is composed of |
153 | its \a name, its \a type, its \a access rights, and, optionally, annotations. |
154 | */ |
155 | |
156 | /*! |
157 | \variable QDBusIntrospection::Property::name |
158 | The property's name. |
159 | */ |
160 | |
161 | /*! |
162 | \variable QDBusIntrospection::Property::type |
163 | The property's type. |
164 | */ |
165 | |
166 | /*! |
167 | \enum QDBusIntrospection::Property::Access |
168 | The possible access rights for a property: |
169 | \value Read |
170 | \value Write |
171 | \value ReadWrite |
172 | */ |
173 | |
174 | /*! |
175 | \variable QDBusIntrospection::Property::access |
176 | The property's access rights. |
177 | */ |
178 | |
179 | /*! |
180 | \variable QDBusIntrospection::Property::annotations |
181 | The annotations associated with the property. Each annotation is a pair of strings, where the key |
182 | is of the same format as a D-Bus interface name. The value is arbitrary. |
183 | */ |
184 | |
185 | /*! |
186 | \fn QDBusIntrospection::Property::operator==(const Property &other) const |
187 | Compares this object against \a other and return true if they are the same. |
188 | */ |
189 | |
190 | /*! |
191 | \class QDBusIntrospection::Interface |
192 | \brief Information about one interface on the bus. |
193 | |
194 | Each interface on D-Bus has an unique \a name, identifying where that interface was defined. |
195 | Interfaces may have annotations, methods, signals and properties, but none are mandatory. |
196 | */ |
197 | |
198 | /*! |
199 | \variable QDBusIntrospection::Interface::name |
200 | The interface's name. |
201 | */ |
202 | |
203 | /*! |
204 | \variable QDBusIntrospection::Interface::introspection |
205 | The XML document fragment describing this interface. |
206 | |
207 | If parsed again through parseInterface, the object returned should have the same contents as |
208 | this object. |
209 | */ |
210 | |
211 | /*! |
212 | \variable QDBusIntrospection::Interface::annotations |
213 | The annotations associated with the interface. Each annotation is a pair of strings, where the key |
214 | is of the same format as a D-Bus interface name. The value is arbitrary. |
215 | */ |
216 | |
217 | /*! |
218 | \variable QDBusIntrospection::Interface::methods |
219 | The methods available in this interface. Note that method names are not unique (i.e., methods |
220 | can be overloaded with multiple arguments types). |
221 | */ |
222 | |
223 | /*! |
224 | \variable QDBusIntrospection::Interface::signals_ |
225 | The signals available in this interface. Note that signal names are not unique (i.e., signals |
226 | can be overloaded with multiple argument types). |
227 | |
228 | This member is called "signals_" because "signals" is a reserved keyword in Qt. |
229 | */ |
230 | |
231 | /*! |
232 | \variable QDBusIntrospection::Interface::properties |
233 | The properties available in this interface. Property names are unique. |
234 | */ |
235 | |
236 | /*! |
237 | \fn QDBusIntrospection::Interface::operator==(const Interface &other) const |
238 | Compares this object against \a other and return true if they are the same. |
239 | |
240 | Note that two interfaces are considered to be the same if they have the same name. The internal |
241 | structures in the objects are not compared. |
242 | */ |
243 | |
244 | /*! |
245 | \class QDBusIntrospection::Object |
246 | \brief Information about one object on the bus. |
247 | |
248 | An object on the D-Bus bus is represented by its service and path on the service but, unlike |
249 | interfaces, objects are mutable. That is, their contents can change with time. Therefore, |
250 | while the (service, path) pair uniquely identifies an object, the information contained in |
251 | this struct may no longer represent the object. |
252 | |
253 | An object can contain interfaces and child (sub) objects. |
254 | */ |
255 | |
256 | /*! |
257 | \variable QDBusIntrospection::Object::service |
258 | The object's service name. |
259 | |
260 | \sa parseObject(), parseObjectTree() |
261 | */ |
262 | |
263 | /*! |
264 | \variable QDBusIntrospection::Object::path |
265 | The object's path on the service. This is an absolute path. |
266 | |
267 | \sa parseObject(), parseObjectTree() |
268 | */ |
269 | |
270 | /*! |
271 | \variable QDBusIntrospection::Object::introspection |
272 | The XML document fragment describing this object, its interfaces and sub-objects at the time |
273 | of the parsing. |
274 | |
275 | The result of parseObject with this XML data should be the same as the Object struct. |
276 | */ |
277 | |
278 | /*! |
279 | \variable QDBusIntrospection::Object::interfaces |
280 | The list of interface names in this object. |
281 | */ |
282 | |
283 | /*! |
284 | \variable QDBusIntrospection::Object::childObjects |
285 | The list of child object names in this object. Note that this is a relative name, not an |
286 | absolute path. To obtain the absolute path, concatenate with \l |
287 | {QDBusIntrospection::Object::path}{path}. |
288 | */ |
289 | |
290 | /*! |
291 | \class QDBusIntrospection::ObjectTree |
292 | \brief Complete information about one object node and its descendency. |
293 | |
294 | This struct contains the same data as QDBusIntrospection::Object, plus the actual data for the |
295 | interfaces and child (sub) objects that was available in the XML document. |
296 | */ |
297 | |
298 | /*! |
299 | \variable QDBusIntrospection::ObjectTree::interfaceData |
300 | A map of interfaces and their names. |
301 | */ |
302 | |
303 | /*! |
304 | \variable QDBusIntrospection::ObjectTree::childObjectData |
305 | A map of object paths and their data. The map key contains the relative path to the object. |
306 | |
307 | Note this map contains only the child notes that do have information about the sub-object's |
308 | contents. If the XML data did not contain the information, only the object name will be listed |
309 | in childObjects, but not in childObjectData. |
310 | */ |
311 | |
312 | /*! |
313 | \typedef QDBusIntrospection::Annotations |
314 | Contains a QMap of an annotation pair. The annotation's name is stored in the QMap key and |
315 | must be unique. The annotation's value is stored in the QMap's value and is arbitrary. |
316 | */ |
317 | |
318 | /*! |
319 | \typedef QDBusIntrospection::Arguments |
320 | Contains a list of arguments to either a Method or a Signal. The arguments' order is important. |
321 | */ |
322 | |
323 | /*! |
324 | \typedef QDBusIntrospection::Methods |
325 | Contains a QMap of methods and their names. The method's name is stored in the map's key and |
326 | is not necessarily unique. The order in which multiple methods with the same name are stored |
327 | in this map is undefined. |
328 | */ |
329 | |
330 | /*! |
331 | \typedef QDBusIntrospection::Signals |
332 | Contains a QMap of signals and their names. The signal's name is stored in the map's key and |
333 | is not necessarily unique. The order in which multiple signals with the same name are stored |
334 | in this map is undefined. |
335 | */ |
336 | |
337 | /*! |
338 | \typedef QDBusIntrospection::Properties |
339 | Contains a QMap of properties and their names. Each property must have a unique name. |
340 | */ |
341 | |
342 | /*! |
343 | \typedef QDBusIntrospection::Interfaces |
344 | Contains a QMap of interfaces and their names. Each interface has a unique name. |
345 | */ |
346 | |
347 | /*! |
348 | \typedef QDBusIntrospection::Objects |
349 | Contains a QMap of objects and their paths relative to their immediate parent. |
350 | |
351 | \sa parseObjectTree() |
352 | */ |
353 | |
354 | /*! |
355 | Parses the XML document fragment (given by \a xml) containing one interface. |
356 | |
357 | The first element tag in this XML data must be either \<node\> or \<interface\>. If it is |
358 | \<node\>, then the \<interface\> tag must be a child tag of the \<node\> one. |
359 | |
360 | If there are multiple interfaces in this XML data, it is undefined which one will be |
361 | returned. |
362 | */ |
363 | QDBusIntrospection::Interface |
364 | QDBusIntrospection::parseInterface(const QString &xml) |
365 | { |
366 | // be lazy |
367 | Interfaces ifs = parseInterfaces(xml); |
368 | if (ifs.isEmpty()) |
369 | return Interface(); |
370 | |
371 | // return the first in map order (probably alphabetical order) |
372 | return *ifs.constBegin().value(); |
373 | } |
374 | |
375 | /*! |
376 | Parses the XML document fragment (given by \a xml) containing several interfaces. |
377 | |
378 | If the first element tag in this document fragment is \<node\>, the interfaces parsed will |
379 | be those found as child elements of the \<node\> tag. |
380 | */ |
381 | QDBusIntrospection::Interfaces |
382 | QDBusIntrospection::parseInterfaces(const QString &xml) |
383 | { |
384 | QString null; |
385 | QDBusXmlParser parser(null, null, xml); |
386 | return parser.interfaces(); |
387 | } |
388 | |
389 | /*! |
390 | Parses the XML document fragment (given by \a xml) containing one object, found at the service |
391 | \a service and path \a path. |
392 | |
393 | The first element tag in this document must be \<node\>. If that tag does not contain |
394 | a name attribute, the \a path argument will be used to determine the path of this |
395 | object node. |
396 | |
397 | This function does not parse the interfaces contained in the node, nor sub-object's contents. |
398 | It will only list their names. If you need to know their contents, use parseObjectTree. |
399 | */ |
400 | QDBusIntrospection::Object |
401 | QDBusIntrospection::parseObject(const QString &xml, const QString &service, const QString &path) |
402 | { |
403 | QDBusXmlParser parser(service, path, xml); |
404 | QSharedDataPointer<QDBusIntrospection::Object> retval = parser.object(); |
405 | if (!retval) |
406 | return QDBusIntrospection::Object(); |
407 | return *retval; |
408 | } |
409 | |
410 | /*! |
411 | Parses the XML document fragment (given by \a xml) containing one object node and returns all |
412 | the information about the interfaces and sub-objects, found at the service \a service and path |
413 | \a path. |
414 | |
415 | The Objects map returned will contain the absolute path names in the key. |
416 | */ |
417 | QDBusIntrospection::ObjectTree |
418 | QDBusIntrospection::parseObjectTree(const QString &xml, const QString &service, const QString &path) |
419 | { |
420 | QDBusXmlParser parser(service, path, xml); |
421 | QSharedDataPointer<QDBusIntrospection::ObjectTree> retval = parser.objectTree(); |
422 | if (!retval) |
423 | return QDBusIntrospection::ObjectTree(); |
424 | return *retval; |
425 | } |
426 | |
427 | QT_END_NAMESPACE |
428 | |
429 | #endif // QT_NO_DBUS |
430 | |