Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Loading...
Searching...
No Matches
qqnxnavigatoreventnotifier.cpp
Go to the documentation of this file.
1// Copyright (C) 2011 - 2012 Research In Motion
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3// Qt-Security score:significant reason:default
4
6
8
9#include <QtCore/QByteArray>
10#include <QtCore/QDebug>
11#include <QtCore/QList>
12#include <QtCore/QSocketNotifier>
13#include <QtCore/private/qcore_unix_p.h>
14
15#include <errno.h>
16#include <fcntl.h>
17#include <unistd.h>
18#include <sys/types.h>
19#include <sys/stat.h>
20
21QT_BEGIN_NAMESPACE
22
23const char *QQnxNavigatorEventNotifier::navigatorControlPath = "/pps/services/navigator/control";
24const size_t QQnxNavigatorEventNotifier::ppsBufferSize = 4096;
25
26QQnxNavigatorEventNotifier::QQnxNavigatorEventNotifier(QQnxNavigatorEventHandler *eventHandler, QObject *parent)
27 : QObject(parent),
28 m_fd(-1),
29 m_readNotifier(0),
30 m_eventHandler(eventHandler)
31{
32}
33
35{
36 delete m_readNotifier;
37
38 // close connection to navigator
39 if (m_fd != -1)
40 close(m_fd);
41
42 qCDebug(lcQpaQnxNavigatorEvents) << "Navigator event notifier stopped";
43}
44
46{
47 qCDebug(lcQpaQnxNavigatorEvents) << "Navigator event notifier started";
48
49 // open connection to navigator
50 errno = 0;
51 m_fd = open(navigatorControlPath, O_RDWR);
52 if (m_fd == -1) {
53 qCDebug(lcQpaQnxNavigatorEvents, "Failed to open navigator pps: %s", strerror(errno));
54 return;
55 }
56
57 m_readNotifier = new QSocketNotifier(m_fd, QSocketNotifier::Read);
58 connect(m_readNotifier, SIGNAL(activated(QSocketDescriptor)), this, SLOT(readData()));
59}
60
61void QQnxNavigatorEventNotifier::parsePPS(const QByteArray &ppsData, QByteArray &msg, QByteArray &dat, QByteArray &id)
62{
63 qCDebug(lcQpaQnxNavigatorEvents) << Q_FUNC_INFO << "data=" << ppsData;
64
65 // tokenize pps data into lines
66 QList<QByteArray> lines = ppsData.split('\n');
67
68 // validate pps object
69 if (Q_UNLIKELY(lines.empty() || lines.at(0) != "@control"))
70 qFatal("QQNX: unrecognized pps object, data=%s", ppsData.constData());
71
72 // parse pps object attributes and extract values
73 for (int i = 1; i < lines.size(); ++i) {
74
75 // tokenize current attribute
76 const QByteArray &attr = lines.at(i);
77 qCDebug(lcQpaQnxNavigatorEvents) << Q_FUNC_INFO << "attr=" << attr;
78
79 int firstColon = attr.indexOf(':');
80 if (firstColon == -1) {
81 // abort - malformed attribute
82 continue;
83 }
84
85 int secondColon = attr.indexOf(':', firstColon + 1);
86 if (secondColon == -1) {
87 // abort - malformed attribute
88 continue;
89 }
90
91 QByteArray key = attr.left(firstColon);
92 QByteArray value = attr.mid(secondColon + 1);
93
94 qCDebug(lcQpaQnxNavigatorEvents) << Q_FUNC_INFO << "key =" << key << "value =" << value;
95
96 // save attribute value
97 if (key == "msg")
98 msg = value;
99 else if (key == "dat")
100 dat = value;
101 else if (key == "id")
102 id = value;
103 else
104 qFatal("QQNX: unrecognized pps attribute, attr=%s", key.constData());
105 }
106}
107
108void QQnxNavigatorEventNotifier::replyPPS(const QByteArray &res, const QByteArray &id, const QByteArray &dat)
109{
110 // construct pps message
111 QByteArray ppsData = "res::";
112 ppsData += res;
113 ppsData += "\nid::";
114 ppsData += id;
115 if (!dat.isEmpty()) {
116 ppsData += "\ndat::";
117 ppsData += dat;
118 }
119 ppsData += "\n";
120
121 qCDebug(lcQpaQnxNavigatorEvents) << Q_FUNC_INFO << "reply=" << ppsData;
122
123 // send pps message to navigator
124 errno = 0;
125 int bytes = write(m_fd, ppsData.constData(), ppsData.size());
126 if (Q_UNLIKELY(bytes == -1))
127 qFatal("QQNX: failed to write navigator pps, errno=%d", errno);
128}
129
130void QQnxNavigatorEventNotifier::handleMessage(const QByteArray &msg, const QByteArray &dat, const QByteArray &id)
131{
132 qCDebug(lcQpaQnxNavigatorEvents) << Q_FUNC_INFO << "msg=" << msg << ", dat=" << dat << ", id=" << id;
133
134 // check message type
135 if (msg == "orientationCheck") {
136 const bool response = m_eventHandler->handleOrientationCheck(dat.toInt());
137
138 // reply to navigator that (any) orientation is acceptable
139 replyPPS(msg, id, response ? "true" : "false");
140 } else if (msg == "orientation") {
141 m_eventHandler->handleOrientationChange(dat.toInt());
142 replyPPS(msg, id, "");
143 } else if (msg == "SWIPE_DOWN") {
144 m_eventHandler->handleSwipeDown();
145 } else if (msg == "exit") {
146 m_eventHandler->handleExit();
147 } else if (msg == "windowActive") {
148 m_eventHandler->handleWindowGroupActivated(dat);
149 } else if (msg == "windowInactive") {
150 m_eventHandler->handleWindowGroupDeactivated(dat);
151 }
152}
153
154void QQnxNavigatorEventNotifier::readData()
155{
156 qCDebug(lcQpaQnxNavigatorEvents) << "Reading navigator data";
157
158 // allocate buffer for pps data
159 char buffer[ppsBufferSize];
160
161 // attempt to read pps data
162 errno = 0;
163 int bytes = qt_safe_read(m_fd, buffer, ppsBufferSize - 1);
164 if (Q_UNLIKELY(bytes == -1))
165 qFatal("QQNX: failed to read navigator pps, errno=%d", errno);
166
167 // check if pps data was received
168 if (bytes > 0) {
169
170 // ensure data is null terminated
171 buffer[bytes] = '\0';
172
173 // process received message
174 QByteArray ppsData(buffer);
175 QByteArray msg;
176 QByteArray dat;
177 QByteArray id;
178 parsePPS(ppsData, msg, dat, id);
179 handleMessage(msg, dat, id);
180 }
181}
182
183QT_END_NAMESPACE