diff options
Diffstat (limited to 'src/widgeteventhandler.cpp')
-rw-r--r-- | src/widgeteventhandler.cpp | 58 |
1 files changed, 45 insertions, 13 deletions
diff --git a/src/widgeteventhandler.cpp b/src/widgeteventhandler.cpp index e610a41..bdcd20c 100644 --- a/src/widgeteventhandler.cpp +++ b/src/widgeteventhandler.cpp @@ -116,13 +116,13 @@ bool WidgetEventHandler::eventFilter(QObject *object, QEvent *event) } if (QLabel *label = qobject_cast<QLabel *>(widget)) { - events.addEvent((int)widget, EventEntry::TextUpdate); + events.addEvent(idForWidget(widget), EventEntry::TextUpdate); return true; } else if (QTextEdit *textEdit = qobject_cast<QTextEdit *>(widget)) { - events.addEvent((int)widget, EventEntry::TextUpdate); + events.addEvent(idForWidget(widget), EventEntry::TextUpdate); return true; } else if (QPushButton *textEdit = qobject_cast<QPushButton *>(widget)) { - events.addEvent((int)widget, EventEntry::TextUpdate); + events.addEvent(idForWidget(widget), EventEntry::TextUpdate); return true; } else if (!grabbing) { @@ -134,7 +134,7 @@ bool WidgetEventHandler::eventFilter(QObject *object, QEvent *event) if (event->type() == QEvent::Show) { DEBUG << "show" << object; // Add immediate show update if we have an image to serve. - if (events.images.contains((int)widget)) { + if (events.images.contains(idForWidget(widget))) { addShowEvent(widget); } @@ -146,7 +146,7 @@ bool WidgetEventHandler::eventFilter(QObject *object, QEvent *event) if (event->type() == QEvent::Hide) { DEBUG << "hide" << object; - events.addEvent((int)widget, EventEntry::Hide); + events.addEvent(idForWidget(widget), EventEntry::Hide); recursivelyAddHide(widget); } @@ -154,19 +154,19 @@ bool WidgetEventHandler::eventFilter(QObject *object, QEvent *event) QRect geometry = globalGeometry(widget); DEBUG << "move geometry" << object->metaObject()->className() << geometry; if (disableUpdates.contains(sender()) == false) - events.addGeometryEvent((int)widget, geometry); + events.addGeometryEvent(idForWidget(widget), geometry); } if (event->type() == QEvent::Resize) { QRect geometry = globalGeometry(widget); DEBUG << "resize geometry" << geometry; - events.addGeometryEvent((int)widget, geometry); + events.addGeometryEvent(idForWidget(widget), geometry); } if (event->type() == QEvent::ParentChange) { DEBUG << "parentChange" << "parent"<< widget->parentWidget() << "child" << widget; - events.addParentChangeEvent((int)widget); + events.addParentChangeEvent(idForWidget(widget)); } return false; @@ -208,6 +208,32 @@ void WidgetEventHandler::handleRequest(HttpRequest *request, HttpResponse *respo } } +// Keep track of the current live widgets, to avoid dereferencing +// stale widget pointers when clients sends updated for a certain +// widget id. This also protects against malicious clients that +// sends fake ids. +quintptr WidgetEventHandler::idForWidget(QWidget *widget) +{ + quintptr id = reinterpret_cast<quintptr>(widget); + if (liveWidgets.contains(id) == false) { + liveWidgets.insert(id); + connect(widget, SIGNAL(destroyed()), SLOT(widgetDeleted())); + } + return id; +} + +QWidget *WidgetEventHandler::widgetForId(quintptr id) +{ + if (liveWidgets.contains(id)) + return reinterpret_cast<QWidget *>(id); + return 0; +} + +void WidgetEventHandler::widgetDeleted() +{ + liveWidgets.remove(reinterpret_cast<quintptr>(sender())); +} + bool WidgetEventHandler::handleJsonMessage(const QByteArray &message) { QByteArray jsonText = QUrl::fromPercentEncoding(message.mid(5)).toUtf8(); // remove "/json", decode. @@ -238,11 +264,12 @@ void WidgetEventHandler::handleMousePress(const QByteArray &message) QPoint p(tokens.at(1).toInt(), tokens.at(2).toInt()); // ### assumes well-formed string QWidget *target = findEventTarget(rootWidget, p); -// DEBUG << "target" << target; + qDebug() << "target" << target << target->metaObject()->className(); QPoint local = target->mapFrom(rootWidget, p); if (message.startsWith("/mousepress")) { + qDebug() << "press" << local; QMouseEvent press(QEvent::MouseButtonPress, local , Qt::LeftButton, Qt::LeftButton, Qt::NoModifier); QApplication::sendEvent(target, &press); } else if (message.startsWith("/mouserelease")) { @@ -288,7 +315,9 @@ void WidgetEventHandler::handleTextUpdate(json_object* request) json_object* tmp = json_object_object_get(request, "text"); QByteArray text = json_object_get_string(tmp); - QWidget *widget = reinterpret_cast<QWidget *>(id); + QWidget *widget = widgetForId(id); + if (!widget) + return; disableUpdates.insert(widget); if (text == "\n") { @@ -306,7 +335,10 @@ void WidgetEventHandler::handlePositionUpdate(json_object *request) const int x = json_object_get_int(json_object_object_get(request, "x")); const int y = json_object_get_int(json_object_object_get(request, "y")); - QWidget *widget = ((QWidget *)(id)); + QWidget *widget = widgetForId(id); + if (!widget) + return; + disableUpdates.insert(widget); widget->move(x, y); disableUpdates.remove(widget); @@ -332,10 +364,10 @@ void WidgetEventHandler::widgetPaint(QWidget *widget, const QRect &updateRect) // DEBUG << "update" << widget << (int)widget; - events.addUpdateEvent((int)widget, image, updateRect); + events.addUpdateEvent(idForWidget(widget), image, updateRect); // DEBUG << "geometry" << widget << (int)widget << globalGeometry(widget); - events.addGeometryEvent((int)widget, globalGeometry(widget)); + events.addGeometryEvent(idForWidget(widget), globalGeometry(widget)); } QRect WidgetEventHandler::globalGeometry(QWidget *widget) |