summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/plugins/platforms/bsdfb/bsdfb.json3
-rw-r--r--src/plugins/platforms/bsdfb/bsdfb.pro15
-rw-r--r--src/plugins/platforms/bsdfb/main.cpp60
-rw-r--r--src/plugins/platforms/bsdfb/qbsdfbintegration.cpp142
-rw-r--r--src/plugins/platforms/bsdfb/qbsdfbintegration.h81
-rw-r--r--src/plugins/platforms/bsdfb/qbsdfbscreen.cpp276
-rw-r--r--src/plugins/platforms/bsdfb/qbsdfbscreen.h74
-rw-r--r--src/plugins/platforms/platforms.pro4
8 files changed, 655 insertions, 0 deletions
diff --git a/src/plugins/platforms/bsdfb/bsdfb.json b/src/plugins/platforms/bsdfb/bsdfb.json
new file mode 100644
index 0000000000..97b3e7707e
--- /dev/null
+++ b/src/plugins/platforms/bsdfb/bsdfb.json
@@ -0,0 +1,3 @@
+{
+ "Keys": [ "bsdfb" ]
+}
diff --git a/src/plugins/platforms/bsdfb/bsdfb.pro b/src/plugins/platforms/bsdfb/bsdfb.pro
new file mode 100644
index 0000000000..c24d8dd9e5
--- /dev/null
+++ b/src/plugins/platforms/bsdfb/bsdfb.pro
@@ -0,0 +1,15 @@
+TARGET = qbsdfb
+
+QT += core-private gui-private platformsupport-private
+
+SOURCES = main.cpp qbsdfbintegration.cpp qbsdfbscreen.cpp
+HEADERS = qbsdfbintegration.h qbsdfbscreen.h
+
+CONFIG += qpa/genericunixfontdatabase
+
+OTHER_FILES += bsdfb.json
+
+PLUGIN_TYPE = platforms
+PLUGIN_CLASS_NAME = QBsdFbIntegrationPlugin
+!equals(TARGET, $$QT_DEFAULT_QPA_PLUGIN): PLUGIN_EXTENDS = -
+load(qt_plugin)
diff --git a/src/plugins/platforms/bsdfb/main.cpp b/src/plugins/platforms/bsdfb/main.cpp
new file mode 100644
index 0000000000..f4ab3dee39
--- /dev/null
+++ b/src/plugins/platforms/bsdfb/main.cpp
@@ -0,0 +1,60 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Copyright (C) 2015-2016 Oleksandr Tymoshenko <gonzo@bluezbox.com>
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL21$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 or version 3 as published by the Free
+** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+** following information to ensure the GNU Lesser General Public License
+** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** As a special exception, The Qt Company gives you certain additional
+** rights. These rights are described in The Qt Company LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include <qpa/qplatformintegrationplugin.h>
+#include "qbsdfbintegration.h"
+
+QT_BEGIN_NAMESPACE
+
+class QBsdFbIntegrationPlugin : public QPlatformIntegrationPlugin
+{
+ Q_OBJECT
+ Q_PLUGIN_METADATA(IID QPlatformIntegrationFactoryInterface_iid FILE "bsdfb.json")
+public:
+ QPlatformIntegration *create(const QString&, const QStringList&) override;
+};
+
+QPlatformIntegration* QBsdFbIntegrationPlugin::create(const QString& system, const QStringList& paramList)
+{
+ Q_UNUSED(paramList);
+ if (!system.compare(QLatin1String("bsdfb"), Qt::CaseInsensitive))
+ return new QBsdFbIntegration(paramList);
+
+ return nullptr;
+}
+
+QT_END_NAMESPACE
+
+#include "main.moc"
+
diff --git a/src/plugins/platforms/bsdfb/qbsdfbintegration.cpp b/src/plugins/platforms/bsdfb/qbsdfbintegration.cpp
new file mode 100644
index 0000000000..edb4f4e660
--- /dev/null
+++ b/src/plugins/platforms/bsdfb/qbsdfbintegration.cpp
@@ -0,0 +1,142 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Copyright (C) 2015-2016 Oleksandr Tymoshenko <gonzo@bluezbox.com>
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL21$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 or version 3 as published by the Free
+** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+** following information to ensure the GNU Lesser General Public License
+** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** As a special exception, The Qt Company gives you certain additional
+** rights. These rights are described in The Qt Company LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qbsdfbintegration.h"
+#include "qbsdfbscreen.h"
+
+#include <QtPlatformSupport/private/qgenericunixfontdatabase_p.h>
+#include <QtPlatformSupport/private/qgenericunixservices_p.h>
+#include <QtPlatformSupport/private/qgenericunixeventdispatcher_p.h>
+
+#include <QtPlatformSupport/private/qfbvthandler_p.h>
+#include <QtPlatformSupport/private/qfbbackingstore_p.h>
+#include <QtPlatformSupport/private/qfbwindow_p.h>
+#include <QtPlatformSupport/private/qfbcursor_p.h>
+
+#include <QtGui/private/qguiapplication_p.h>
+#include <qpa/qplatforminputcontext.h>
+#include <qpa/qplatforminputcontextfactory_p.h>
+
+#if !defined(QT_NO_TSLIB)
+#include <QtPlatformSupport/private/qtslib_p.h>
+#endif
+
+QT_BEGIN_NAMESPACE
+
+QBsdFbIntegration::QBsdFbIntegration(const QStringList &paramList)
+{
+ m_fontDb.reset(new QGenericUnixFontDatabase);
+ m_services.reset(new QGenericUnixServices);
+ m_primaryScreen.reset(new QBsdFbScreen(paramList));
+}
+
+QBsdFbIntegration::~QBsdFbIntegration()
+{
+ destroyScreen(m_primaryScreen.data());
+}
+
+void QBsdFbIntegration::initialize()
+{
+ if (m_primaryScreen->initialize())
+ screenAdded(m_primaryScreen.data());
+ else
+ qWarning("bsdfb: Failed to initialize screen");
+
+ m_inputContext.reset(QPlatformInputContextFactory::create());
+ m_nativeInterface.reset(new QPlatformNativeInterface);
+ m_vtHandler.reset(new QFbVtHandler);
+
+ if (!qEnvironmentVariableIntValue("QT_QPA_FB_DISABLE_INPUT"))
+ createInputHandlers();
+}
+
+bool QBsdFbIntegration::hasCapability(QPlatformIntegration::Capability cap) const
+{
+ switch (cap) {
+ case ThreadedPixmaps:
+ return true;
+ case WindowManagement:
+ return false;
+ default:
+ return QPlatformIntegration::hasCapability(cap);
+ }
+}
+
+QPlatformBackingStore *QBsdFbIntegration::createPlatformBackingStore(QWindow *window) const
+{
+ return new QFbBackingStore(window);
+}
+
+QPlatformWindow *QBsdFbIntegration::createPlatformWindow(QWindow *window) const
+{
+ return new QFbWindow(window);
+}
+
+QAbstractEventDispatcher *QBsdFbIntegration::createEventDispatcher() const
+{
+ return createUnixEventDispatcher();
+}
+
+QList<QPlatformScreen *> QBsdFbIntegration::screens() const
+{
+ QList<QPlatformScreen *> list;
+ list.append(m_primaryScreen.data());
+ return list;
+}
+
+QPlatformFontDatabase *QBsdFbIntegration::fontDatabase() const
+{
+ return m_fontDb.data();
+}
+
+QPlatformServices *QBsdFbIntegration::services() const
+{
+ return m_services.data();
+}
+
+void QBsdFbIntegration::createInputHandlers()
+{
+#ifndef QT_NO_TSLIB
+ const bool useTslib = qEnvironmentVariableIntValue("QT_QPA_FB_TSLIB");
+ if (useTslib)
+ new QTsLibMouseHandler(QLatin1String("TsLib"), QString());
+#endif
+}
+
+QPlatformNativeInterface *QBsdFbIntegration::nativeInterface() const
+{
+ return m_nativeInterface.data();
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/platforms/bsdfb/qbsdfbintegration.h b/src/plugins/platforms/bsdfb/qbsdfbintegration.h
new file mode 100644
index 0000000000..2be5ea260d
--- /dev/null
+++ b/src/plugins/platforms/bsdfb/qbsdfbintegration.h
@@ -0,0 +1,81 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL21$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 or version 3 as published by the Free
+** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+** following information to ensure the GNU Lesser General Public License
+** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** As a special exception, The Qt Company gives you certain additional
+** rights. These rights are described in The Qt Company LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QBSDFBINTEGRATION_H
+#define QBSDFBINTEGRATION_H
+
+#include <qpa/qplatformintegration.h>
+#include <qpa/qplatformnativeinterface.h>
+
+QT_BEGIN_NAMESPACE
+
+class QAbstractEventDispatcher;
+class QBsdFbScreen;
+class QFbVtHandler;
+
+class QBsdFbIntegration : public QPlatformIntegration, public QPlatformNativeInterface
+{
+public:
+ explicit QBsdFbIntegration(const QStringList &paramList);
+ ~QBsdFbIntegration() override;
+
+ void initialize() override;
+ bool hasCapability(QPlatformIntegration::Capability cap) const override;
+
+ QPlatformWindow *createPlatformWindow(QWindow *window) const override;
+ QPlatformBackingStore *createPlatformBackingStore(QWindow *window) const override;
+
+ QAbstractEventDispatcher *createEventDispatcher() const override;
+
+ QPlatformFontDatabase *fontDatabase() const override;
+ QPlatformServices *services() const override;
+ QPlatformInputContext *inputContext() const override { return m_inputContext.data(); }
+
+ QPlatformNativeInterface *nativeInterface() const override;
+
+ QList<QPlatformScreen *> screens() const;
+
+private:
+ void createInputHandlers();
+
+ QScopedPointer<QBsdFbScreen> m_primaryScreen;
+ QScopedPointer<QPlatformInputContext> m_inputContext;
+ QScopedPointer<QPlatformFontDatabase> m_fontDb;
+ QScopedPointer<QPlatformServices> m_services;
+ QScopedPointer<QFbVtHandler> m_vtHandler;
+ QScopedPointer<QPlatformNativeInterface> m_nativeInterface;
+};
+
+QT_END_NAMESPACE
+
+#endif // QBSDFBINTEGRATION_H
diff --git a/src/plugins/platforms/bsdfb/qbsdfbscreen.cpp b/src/plugins/platforms/bsdfb/qbsdfbscreen.cpp
new file mode 100644
index 0000000000..ee2dce6867
--- /dev/null
+++ b/src/plugins/platforms/bsdfb/qbsdfbscreen.cpp
@@ -0,0 +1,276 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Copyright (C) 2015-2016 Oleksandr Tymoshenko <gonzo@bluezbox.com>
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL21$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 or version 3 as published by the Free
+** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+** following information to ensure the GNU Lesser General Public License
+** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** As a special exception, The Qt Company gives you certain additional
+** rights. These rights are described in The Qt Company LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qbsdfbscreen.h"
+#include <QtPlatformSupport/private/qfbcursor_p.h>
+#include <QtPlatformSupport/private/qfbwindow_p.h>
+#include <QtCore/QRegularExpression>
+#include <QtGui/QPainter>
+
+#include <private/qcore_unix_p.h> // overrides QT_OPEN
+#include <qimage.h>
+#include <qdebug.h>
+
+#include <unistd.h>
+#include <stdlib.h>
+#include <sys/ioctl.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <sys/mman.h>
+#include <fcntl.h>
+#include <errno.h>
+#include <stdio.h>
+#include <limits.h>
+#include <signal.h>
+
+#include <sys/consio.h>
+#include <sys/fbio.h>
+
+QT_BEGIN_NAMESPACE
+
+enum {
+ DefaultDPI = 100
+};
+
+static int openFramebufferDevice(const QString &dev)
+{
+ const QByteArray devPath = QFile::encodeName(dev);
+
+ int fd = QT_OPEN(devPath.constData(), O_RDWR);
+
+ if (fd == -1)
+ fd = QT_OPEN(devPath.constData(), O_RDONLY);
+
+ return fd;
+}
+
+static QRect determineGeometry(const struct fbtype &fb, const QRect &userGeometry)
+{
+ int xoff = 0;
+ int yoff = 0;
+ int w = 0;
+ int h = 0;
+
+ if (userGeometry.isValid()) {
+ w = qMin(userGeometry.width(), fb.fb_width);
+ h = qMin(userGeometry.height(), fb.fb_height);
+
+ int xxoff = userGeometry.x(), yyoff = userGeometry.y();
+ if (xxoff != 0 || yyoff != 0) {
+ if (xxoff < 0 || xxoff + w > fb.fb_width)
+ xxoff = fb.fb_width - w;
+ if (yyoff < 0 || yyoff + h > fb.fb_height)
+ yyoff = fb.fb_height - h;
+ xoff += xxoff;
+ yoff += yyoff;
+ } else {
+ xoff += (fb.fb_width - w)/2;
+ yoff += (fb.fb_height - h)/2;
+ }
+ } else {
+ w = fb.fb_width;
+ h = fb.fb_height;
+ }
+
+ if (w == 0 || h == 0) {
+ qWarning("Unable to find screen geometry, using 320x240");
+ w = 320;
+ h = 240;
+ }
+
+ return QRect(xoff, yoff, w, h);
+}
+
+static QSizeF determinePhysicalSize(const QSize &mmSize, const QSize &res)
+{
+ int mmWidth = mmSize.width();
+ int mmHeight = mmSize.height();
+
+ if (mmWidth <= 0 && mmHeight <= 0) {
+ const int dpi = DefaultDPI;
+ mmWidth = qRound(res.width() * 25.4 / dpi);
+ mmHeight = qRound(res.height() * 25.4 / dpi);
+ } else if (mmWidth > 0 && mmHeight <= 0) {
+ mmHeight = res.height() * mmWidth/res.width();
+ } else if (mmHeight > 0 && mmWidth <= 0) {
+ mmWidth = res.width() * mmHeight/res.height();
+ }
+
+ return QSize(mmWidth, mmHeight);
+}
+
+QBsdFbScreen::QBsdFbScreen(const QStringList &args)
+ : m_arguments(args)
+{
+}
+
+QBsdFbScreen::~QBsdFbScreen()
+{
+ if (m_framebufferFd != -1) {
+ munmap(m_mmap.data - m_mmap.offset, m_mmap.size);
+ qt_safe_close(m_framebufferFd);
+ }
+}
+
+bool QBsdFbScreen::initialize()
+{
+ QRegularExpression fbRx(QLatin1String("fb=(.*)"));
+ QRegularExpression mmSizeRx(QLatin1String("mmsize=(\\d+)x(\\d+)"));
+ QRegularExpression sizeRx(QLatin1String("size=(\\d+)x(\\d+)"));
+ QRegularExpression offsetRx(QLatin1String("offset=(\\d+)x(\\d+)"));
+
+ QString fbDevice;
+ QSize userMmSize;
+ QRect userGeometry;
+
+ // Parse arguments
+ for (const QString &arg : qAsConst(m_arguments)) {
+ QRegularExpressionMatch match;
+ if (arg.contains(mmSizeRx, &match))
+ userMmSize = QSize(match.captured(1).toInt(), match.captured(2).toInt());
+ else if (arg.contains(sizeRx, &match))
+ userGeometry.setSize(QSize(match.captured(1).toInt(), match.captured(2).toInt()));
+ else if (arg.contains(offsetRx, &match))
+ userGeometry.setTopLeft(QPoint(match.captured(1).toInt(), match.captured(2).toInt()));
+ else if (arg.contains(fbRx, &match))
+ fbDevice = match.captured(1);
+ }
+
+ if (!fbDevice.isEmpty()) {
+ // Open the device
+ m_framebufferFd = openFramebufferDevice(fbDevice);
+ } else {
+ m_framebufferFd = STDIN_FILENO;
+ }
+
+ if (m_framebufferFd == -1) {
+ qErrnoWarning(errno, "Failed to open framebuffer %s", qPrintable(fbDevice));
+ return false;
+ }
+
+ struct fbtype fb;
+ if (ioctl(m_framebufferFd, FBIOGTYPE, &fb) != 0) {
+ qErrnoWarning(errno, "Error reading framebuffer information");
+ return false;
+ }
+
+ int line_length = 0;
+ if (ioctl(m_framebufferFd, FBIO_GETLINEWIDTH, &line_length) != 0) {
+ qErrnoWarning(errno, "Error reading line length information");
+ return false;
+ }
+
+ mDepth = fb.fb_depth;
+
+ m_bytesPerLine = line_length;
+ const QRect geometry = determineGeometry(fb, userGeometry);
+ mGeometry = QRect(QPoint(0, 0), geometry.size());
+ switch (mDepth) {
+ case 32:
+ mFormat = QImage::Format_RGB32;
+ break;
+ case 24:
+ mFormat = QImage::Format_RGB888;
+ break;
+ case 16:
+ // falling back
+ default:
+ mFormat = QImage::Format_RGB16;
+ break;
+ }
+ mPhysicalSize = determinePhysicalSize(userMmSize, geometry.size());
+
+ // mmap the framebuffer
+ const size_t pagemask = getpagesize() - 1;
+ m_mmap.size = (m_bytesPerLine * fb.fb_height + pagemask) & ~pagemask;
+ uchar *data = static_cast<uchar*>(mmap(nullptr, m_mmap.size, PROT_READ | PROT_WRITE, MAP_SHARED, m_framebufferFd, 0));
+ if (data == MAP_FAILED) {
+ qErrnoWarning(errno, "Failed to mmap framebuffer");
+ return false;
+ }
+
+ m_mmap.offset = geometry.y() * m_bytesPerLine + geometry.x() * mDepth / 8;
+ m_mmap.data = data + m_mmap.offset;
+
+ QFbScreen::initializeCompositor();
+ m_onscreenImage = QImage(m_mmap.data, geometry.width(), geometry.height(), m_bytesPerLine, mFormat);
+
+ mCursor = new QFbCursor(this);
+
+ return true;
+}
+
+QRegion QBsdFbScreen::doRedraw()
+{
+ const QRegion touched = QFbScreen::doRedraw();
+
+ if (touched.isEmpty())
+ return touched;
+
+ if (!m_blitter)
+ m_blitter.reset(new QPainter(&m_onscreenImage));
+
+ const auto rects = touched.rects();
+ for (const QRect &rect : rects)
+ m_blitter->drawImage(rect, *mScreenImage, rect);
+ return touched;
+}
+
+// grabWindow() grabs "from the screen" not from the backingstores.
+QPixmap QBsdFbScreen::grabWindow(WId wid, int x, int y, int width, int height) const
+{
+ if (!wid) {
+ if (width < 0)
+ width = m_onscreenImage.width() - x;
+ if (height < 0)
+ height = m_onscreenImage.height() - y;
+ return QPixmap::fromImage(m_onscreenImage).copy(x, y, width, height);
+ }
+
+ const QFbWindow *window = windowForId(wid);
+ if (window) {
+ const QRect geom = window->geometry();
+ if (width < 0)
+ width = geom.width() - x;
+ if (height < 0)
+ height = geom.height() - y;
+ QRect rect(geom.topLeft() + QPoint(x, y), QSize(width, height));
+ rect &= window->geometry();
+ return QPixmap::fromImage(m_onscreenImage).copy(rect);
+ }
+
+ return QPixmap();
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/platforms/bsdfb/qbsdfbscreen.h b/src/plugins/platforms/bsdfb/qbsdfbscreen.h
new file mode 100644
index 0000000000..0d9964afd5
--- /dev/null
+++ b/src/plugins/platforms/bsdfb/qbsdfbscreen.h
@@ -0,0 +1,74 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 The Qt Company Ltd.
+** Copyright (C) 2015-2016 Oleksandr Tymoshenko <gonzo@bluezbox.com>
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL21$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 or version 3 as published by the Free
+** Software Foundation and appearing in the file LICENSE.LGPLv21 and
+** LICENSE.LGPLv3 included in the packaging of this file. Please review the
+** following information to ensure the GNU Lesser General Public License
+** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** As a special exception, The Qt Company gives you certain additional
+** rights. These rights are described in The Qt Company LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QBSDFBSCREEN_H
+#define QBSDFBSCREEN_H
+
+#include <QtPlatformSupport/private/qfbscreen_p.h>
+
+QT_BEGIN_NAMESPACE
+
+class QPainter;
+
+class QBsdFbScreen : public QFbScreen
+{
+ Q_OBJECT
+public:
+ explicit QBsdFbScreen(const QStringList &args);
+ ~QBsdFbScreen() override;
+
+ bool initialize();
+
+ QPixmap grabWindow(WId wid, int x, int y, int width, int height) const override;
+
+ QRegion doRedraw() override;
+
+private:
+ QStringList m_arguments;
+ int m_framebufferFd = -1;
+ QImage m_onscreenImage;
+
+ int m_bytesPerLine = -1;
+
+ struct {
+ uchar *data;
+ int offset, size;
+ } m_mmap;
+
+ QScopedPointer<QPainter> m_blitter;
+};
+
+QT_END_NAMESPACE
+
+#endif // QBSDFBSCREEN_H
diff --git a/src/plugins/platforms/platforms.pro b/src/plugins/platforms/platforms.pro
index a63fc28a66..b447cf9b81 100644
--- a/src/plugins/platforms/platforms.pro
+++ b/src/plugins/platforms/platforms.pro
@@ -35,6 +35,10 @@ contains(QT_CONFIG, directfb) {
contains(QT_CONFIG, linuxfb): SUBDIRS += linuxfb
+freebsd {
+ SUBDIRS += bsdfb
+}
+
haiku {
SUBDIRS += haiku
}