aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJesse Barker <jesse.barker@linaro.org>2012-12-18 07:42:46 -0800
committerJesse Barker <jesse.barker@linaro.org>2012-12-18 07:42:46 -0800
commit12b72c5e2ce4154077504820f09e3f4ac13c5dc7 (patch)
tree2c23e0b825cd001553d1b6da2150e4460f894807
parent6bd7e1c7b7aa65a2f473c0d4dedd0f47d084b848 (diff)
parent4be027a005d8d6dec3b4ce2317527fab424e08ac (diff)
downloadglmark2-12b72c5e2ce4154077504820f09e3f4ac13c5dc7.tar.gz
Merge of lp:~glmark2-dev/glmark2/canvas-drm-rebranch
Adds CanvasDRM, which uses GBM and KMS APIs to manage surfaces and modesetting, respectively. Allows glmark2 to run on a console and take over the framebuffer directly (no window/display manager).
-rw-r--r--INSTALL2
-rw-r--r--src/canvas-drm.cpp587
-rw-r--r--src/canvas-drm.h132
-rw-r--r--src/main.cpp8
-rw-r--r--src/wscript_build43
-rw-r--r--wscript36
6 files changed, 797 insertions, 11 deletions
diff --git a/INSTALL b/INSTALL
index 550631a..4f65d23 100644
--- a/INSTALL
+++ b/INSTALL
@@ -2,7 +2,7 @@ glmark2 uses the WAF build system.
To configure glmark2 use:
-$ ./waf configure [--enable-gl --enable-glesv2 --data-path=DATA_PATH --prefix=PREFIX]
+$ ./waf configure [--enable-gl --enable-glesv2 --enable-gl-drm --enable-glesv2-drm --data-path=DATA_PATH --prefix=PREFIX]
To build use:
diff --git a/src/canvas-drm.cpp b/src/canvas-drm.cpp
new file mode 100644
index 0000000..7d11e85
--- /dev/null
+++ b/src/canvas-drm.cpp
@@ -0,0 +1,587 @@
+//
+// Copyright © 2012 Linaro Limited
+//
+// This file is part of the glmark2 OpenGL (ES) 2.0 benchmark.
+//
+// glmark2 is free software: you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the Free Software
+// Foundation, either version 3 of the License, or (at your option) any later
+// version.
+//
+// glmark2 is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
+// FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
+// details.
+//
+// You should have received a copy of the GNU General Public License along with
+// glmark2. If not, see <http://www.gnu.org/licenses/>.
+//
+// Authors:
+// Simon Que
+// Jesse Barker
+//
+#include "canvas-drm.h"
+#include "log.h"
+#include "options.h"
+#include "util.h"
+
+#include <fcntl.h>
+#include <poll.h>
+#include <signal.h>
+#include <string.h>
+#include <time.h>
+
+#include <fstream>
+#include <sstream>
+#include <list>
+
+/******************
+ * Public methods *
+ ******************/
+
+bool
+CanvasDRM::reset()
+{
+ if (!reset_context())
+ return false;
+
+ if (!make_current())
+ return false;
+
+ if (!supports_gl2()) {
+ Log::error("Glmark2 needs OpenGL(ES) version >= 2.0 to run"
+ " (but version string is: '%s')!\n",
+ glGetString(GL_VERSION));
+ return false;
+ }
+
+ glViewport(0, 0, width_, height_);
+ glEnable(GL_DEPTH_TEST);
+ glDepthFunc(GL_LEQUAL);
+ glEnable(GL_CULL_FACE);
+ glCullFace(GL_BACK);
+
+ clear();
+ egl_.swap();
+
+ if (!drm_.reset()) {
+ return false;
+ }
+
+ return true;
+}
+
+void
+DRMState::fb_destroy_callback(gbm_bo* bo, void* data)
+{
+ DRMFBState* fb = reinterpret_cast<DRMFBState*>(data);
+ if (fb && fb->fb_id) {
+ drmModeRmFB(fb->fd, fb->fb_id);
+ }
+ delete fb;
+ gbm_device* dev = gbm_bo_get_device(bo);
+ Log::debug("Got GBM device handle %p from buffer object\n", dev);
+}
+
+DRMFBState*
+DRMState::fb_get_from_bo(gbm_bo* bo)
+{
+ DRMFBState* fb = reinterpret_cast<DRMFBState*>(gbm_bo_get_user_data(bo));
+ if (fb) {
+ return fb;
+ }
+
+ unsigned int width = gbm_bo_get_width(bo);
+ unsigned int height = gbm_bo_get_height(bo);
+ unsigned int stride = gbm_bo_get_stride(bo);
+ unsigned int handle = gbm_bo_get_handle(bo).u32;
+ unsigned int fb_id(0);
+ int status = drmModeAddFB(fd_, width, height, 24, 32, stride, handle, &fb_id);
+ if (status < 0) {
+ Log::error("Failed to create FB: %d\n", status);
+ return 0;
+ }
+
+ fb = new DRMFBState();
+ fb->fd = fd_;
+ fb->bo = bo;
+ fb->fb_id = fb_id;
+
+ gbm_bo_set_user_data(bo, fb, fb_destroy_callback);
+ return fb;
+}
+
+bool
+DRMState::init_gbm()
+{
+ dev_ = gbm_create_device(fd_);
+ if (!dev_) {
+ Log::error("Failed to create GBM device\n");
+ return false;
+ }
+
+ surface_ = gbm_surface_create(dev_, mode_->hdisplay, mode_->vdisplay,
+ GBM_FORMAT_XRGB8888,
+ GBM_BO_USE_SCANOUT | GBM_BO_USE_RENDERING);
+ if (!surface_) {
+ Log::error("Failed to create GBM surface\n");
+ return false;
+ }
+
+ return true;
+}
+
+bool
+DRMState::init()
+{
+ // TODO: Replace this with something that explicitly probes for the loaded
+ // driver (udev?).
+ static const char* drm_modules[] = {
+ "i915",
+ "nouveau",
+ "radeon",
+ "vmgfx",
+ "omapdrm",
+ "exynos"
+ };
+
+ unsigned int num_modules(sizeof(drm_modules)/sizeof(drm_modules[0]));
+ for (unsigned int m = 0; m < num_modules; m++) {
+ fd_ = drmOpen(drm_modules[m], 0);
+ if (fd_ < 0) {
+ Log::debug("Failed to open DRM module '%s'\n", drm_modules[m]);
+ continue;
+ }
+ Log::debug("Opened DRM module '%s'\n", drm_modules[m]);
+ break;
+ }
+
+ if (fd_ < 0) {
+ Log::error("Failed to find a suitable DRM device\n");
+ return false;
+ }
+
+ resources_ = drmModeGetResources(fd_);
+ if (!resources_) {
+ Log::error("drmModeGetResources failed\n");
+ return false;
+ }
+
+ // Find a connected connector
+ for (int c = 0; c < resources_->count_connectors; c++) {
+ connector_ = drmModeGetConnector(fd_, resources_->connectors[c]);
+ if (DRM_MODE_CONNECTED == connector_->connection) {
+ break;
+ }
+ drmModeFreeConnector(connector_);
+ connector_ = 0;
+ }
+
+ if (!connector_) {
+ Log::error("Failed to find a suitable connector\n");
+ return false;
+ }
+
+ // Find the best resolution (we will always operate full-screen).
+ unsigned int bestArea(0);
+ for (int m = 0; m < connector_->count_modes; m++) {
+ drmModeModeInfo* curMode = &connector_->modes[m];
+ unsigned int curArea = curMode->hdisplay * curMode->vdisplay;
+ if (curArea > bestArea) {
+ mode_ = curMode;
+ bestArea = curArea;
+ }
+ }
+
+ if (!mode_) {
+ Log::error("Failed to find a suitable mode\n");
+ return false;
+ }
+
+ // Find a suitable encoder
+ for (int e = 0; e < resources_->count_encoders; e++) {
+ encoder_ = drmModeGetEncoder(fd_, resources_->encoders[e]);
+ if (encoder_ && encoder_->encoder_id == connector_->encoder_id) {
+ break;
+ }
+ drmModeFreeEncoder(encoder_);
+ encoder_ = 0;
+ }
+
+ if (!encoder_) {
+ Log::error("Failed to find a suitable encoder\n");
+ return false;
+ }
+
+ if (!init_gbm()) {
+ return false;
+ }
+
+ crtc_ = drmModeGetCrtc(fd_, encoder_->crtc_id);
+ if (!crtc_) {
+ Log::error("Failed to get current CRTC\n");
+ return false;
+ }
+
+ signal(SIGINT, &DRMState::quit_handler);
+
+ return true;
+}
+
+bool
+DRMState::reset()
+{
+ if (bo_) {
+ gbm_surface_release_buffer(surface_, bo_);
+ }
+
+ bo_ = gbm_surface_lock_front_buffer(surface_);
+ fb_ = fb_get_from_bo(bo_);
+
+ int status = drmModeSetCrtc(fd_, encoder_->crtc_id, fb_->fb_id, 0, 0,
+ &connector_->connector_id, 1, mode_);
+ if (status < 0) {
+ Log::error("Failed to set CRTC: %d\n", status);
+ return false;
+ }
+
+ return true;
+}
+
+
+bool DRMState::should_quit_ = false;
+
+void
+DRMState::quit_handler(int signo)
+{
+ Log::debug("Got SIGINT (%d).\n", signo);
+ should_quit_ = true;
+}
+void
+DRMState::page_flip_handler(int fd, unsigned int frame, unsigned int sec, unsigned int usec, void* data)
+{
+ unsigned int* waiting = reinterpret_cast<unsigned int*>(data);
+ *waiting = 0;
+ // Deal with unused parameters
+ static_cast<void>(fd);
+ static_cast<void>(frame);
+ static_cast<void>(sec);
+ static_cast<void>(usec);
+}
+
+void
+DRMState::do_flip()
+{
+ gbm_bo* next = gbm_surface_lock_front_buffer(surface_);
+ fb_ = fb_get_from_bo(next);
+ unsigned int waiting(1);
+ int status = drmModePageFlip(fd_, encoder_->crtc_id, fb_->fb_id,
+ DRM_MODE_PAGE_FLIP_EVENT, &waiting);
+ if (status < 0) {
+ Log::error("Failed to enqueue page flip: %d\n", status);
+ return;
+ }
+
+ fd_set fds;
+ FD_ZERO(&fds);
+ FD_SET(fd_, &fds);
+ drmEventContext evCtx;
+ evCtx.version = DRM_EVENT_CONTEXT_VERSION;
+ evCtx.page_flip_handler = page_flip_handler;
+
+ while (waiting) {
+ status = select(fd_ + 1, &fds, 0, 0, 0);
+ if (status < 0) {
+ // Most of the time, select() will return an error because the
+ // user pressed Ctrl-C. So, only print out a message in debug
+ // mode, and just check for the likely condition and release
+ // the current buffer object before getting out.
+ Log::debug("Error in select\n");
+ if (should_quit()) {
+ gbm_surface_release_buffer(surface_, bo_);
+ bo_ = next;
+ }
+ return;
+ }
+ drmHandleEvent(fd_, &evCtx);
+ }
+
+ gbm_surface_release_buffer(surface_, bo_);
+ bo_ = next;
+}
+
+void
+DRMState::cleanup()
+{
+ // Restore CRTC state if necessary
+ if (crtc_) {
+ int status = drmModeSetCrtc(fd_, crtc_->crtc_id, crtc_->buffer_id,
+ crtc_->x, crtc_->y, &connector_->connector_id,
+ 1, &crtc_->mode);
+ if (status < 0) {
+ Log::error("Failed to restore original CRTC: %d\n", status);
+ }
+ drmModeFreeCrtc(crtc_);
+ crtc_ = 0;
+ }
+ if (surface_) {
+ gbm_surface_destroy(surface_);
+ surface_ = 0;
+ }
+ if (dev_) {
+ gbm_device_destroy(dev_);
+ dev_ = 0;
+ }
+ if (connector_) {
+ drmModeFreeConnector(connector_);
+ connector_ = 0;
+ }
+ if (encoder_) {
+ drmModeFreeEncoder(encoder_);
+ encoder_ = 0;
+ }
+ if (resources_) {
+ drmModeFreeResources(resources_);
+ resources_ = 0;
+ }
+ if (fd_ > 0) {
+ drmClose(fd_);
+ }
+ fd_ = 0;
+ mode_ = 0;
+}
+
+bool
+CanvasDRM::init()
+{
+ Log::info("NOTE: The DRM canvas is still experimental and its behavior\n");
+ Log::info(" is subject to change as GBM and modesetting behavior\n");
+ Log::info(" evolves\n");
+
+ if (!drm_.init()) {
+ Log::error("Failed to initialize the DRM canvas\n");
+ drm_.cleanup();
+ return false;
+ }
+
+ width_ = drm_.mode_width();
+ height_ = drm_.mode_height();
+ resize_no_viewport(width_, height_);
+
+ if (!egl_.init_display(drm_.device(), visual_config_)) {
+ return false;
+ }
+ if (!egl_.init_surface(drm_.surface())) {
+ return false;
+ }
+ if (!egl_.valid()) {
+ return false;
+ }
+
+ return reset();
+}
+
+
+CanvasDRM::~CanvasDRM()
+{
+ drm_.cleanup();
+}
+
+void
+CanvasDRM::visible(bool /* visible */)
+{
+}
+
+void
+CanvasDRM::clear()
+{
+ glClearColor(0.0f, 0.0f, 0.0f, 0.5f);
+#if USE_GL
+ glClearDepth(1.0f);
+#elif USE_GLESv2
+ glClearDepthf(1.0f);
+#endif
+ glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+}
+
+void
+CanvasDRM::update()
+{
+ Options::FrameEnd m = Options::frame_end;
+
+ if (m == Options::FrameEndDefault) {
+ if (offscreen_)
+ m = Options::FrameEndFinish;
+ else
+ m = Options::FrameEndSwap;
+ }
+
+ switch(m) {
+ case Options::FrameEndSwap:
+ swap_buffers();
+ break;
+ case Options::FrameEndFinish:
+ glFinish();
+ break;
+ case Options::FrameEndReadPixels:
+ read_pixel(width_ / 2, height_ / 2);
+ break;
+ case Options::FrameEndNone:
+ default:
+ break;
+ }
+}
+
+void
+CanvasDRM::print_info()
+{
+ make_current();
+
+ std::stringstream ss;
+ ss << " OpenGL Information" << std::endl;
+ ss << " GL_VENDOR: " << glGetString(GL_VENDOR) << std::endl;
+ ss << " GL_RENDERER: " << glGetString(GL_RENDERER) << std::endl;
+ ss << " GL_VERSION: " << glGetString(GL_VERSION) << std::endl;
+ Log::info("%s", ss.str().c_str());
+}
+
+Canvas::Pixel
+CanvasDRM::read_pixel(int x, int y)
+{
+ uint8_t pixel[4];
+ glReadPixels(x, y, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, pixel);
+ return Canvas::Pixel(pixel[0], pixel[1], pixel[2], pixel[3]);
+}
+
+void
+CanvasDRM::write_to_file(std::string &filename)
+{
+ char *pixels = new char[width_ * height_ * 4];
+
+ for (int i = 0; i < height_; i++) {
+ glReadPixels(0, i, width_, 1, GL_RGBA, GL_UNSIGNED_BYTE,
+ &pixels[(height_ - i - 1) * width_ * 4]);
+ }
+
+ std::ofstream output (filename.c_str(), std::ios::out | std::ios::binary);
+ output.write(pixels, 4 * width_ * height_);
+
+ delete [] pixels;
+}
+
+bool
+CanvasDRM::should_quit()
+{
+ return drm_.should_quit();
+}
+
+void
+CanvasDRM::resize(int width, int height)
+{
+ resize_no_viewport(width, height);
+ glViewport(0, 0, width_, height_);
+}
+
+/*********************
+ * Protected methods *
+ *********************/
+
+bool
+CanvasDRM::supports_gl2()
+{
+ std::string gl_version_str(
+ reinterpret_cast<const char*>(glGetString(GL_VERSION)));
+ int gl_major = 0;
+
+ size_t point_pos(gl_version_str.find('.'));
+
+ if (point_pos != std::string::npos) {
+ point_pos--;
+
+ size_t start_pos(gl_version_str.rfind(' ', point_pos));
+ if (start_pos == std::string::npos)
+ start_pos = 0;
+ else
+ start_pos++;
+
+ gl_major = Util::fromString<int>(
+ gl_version_str.substr(start_pos, point_pos - start_pos + 1)
+ );
+ }
+
+ return gl_major >= 2;
+}
+
+bool
+CanvasDRM::make_current()
+{
+ if (!egl_.valid()) {
+ Log::error("CanvasDRM: Invalid EGL state\n");
+ return false;
+ }
+
+ init_gl_extensions();
+
+ return true;
+}
+
+bool
+CanvasDRM::reset_context()
+{
+ return egl_.reset();
+}
+
+void
+CanvasDRM::swap_buffers()
+{
+ egl_.swap();
+ drm_.do_flip();
+}
+
+void
+CanvasDRM::init_gl_extensions()
+{
+#if USE_GLESv2
+ /*
+ * Parse the extensions we care about from the extension string.
+ * Don't even bother to get function pointers until we know the
+ * extension is present.
+ */
+ std::string extString;
+ const char* exts =
+ reinterpret_cast<const char*>(glGetString(GL_EXTENSIONS));
+ if (exts)
+ extString = exts;
+
+ if (extString.find("GL_OES_mapbuffer") != std::string::npos) {
+ GLExtensions::MapBuffer = reinterpret_cast<PFNGLMAPBUFFEROESPROC>(
+ eglGetProcAddress("glMapBufferOES"));
+ GLExtensions::UnmapBuffer = reinterpret_cast<PFNGLUNMAPBUFFEROESPROC>(
+ eglGetProcAddress("glUnmapBufferOES"));
+ }
+#elif USE_GL
+ GLExtensions::MapBuffer = glMapBuffer;
+ GLExtensions::UnmapBuffer = glUnmapBuffer;
+#endif
+}
+
+
+/*******************
+ * Private methods *
+ *******************/
+
+void
+CanvasDRM::resize_no_viewport(int width, int height)
+{
+ width_ = drm_.mode_width();
+ height_ = drm_.mode_height();
+
+ if (!width_)
+ width_ = width;
+ if (!height_)
+ height_ = height;
+
+ projection_ =
+ LibMatrix::Mat4::perspective(60.0, width_ / static_cast<float>(height_),
+ 1.0, 1024.0);
+}
diff --git a/src/canvas-drm.h b/src/canvas-drm.h
new file mode 100644
index 0000000..e355131
--- /dev/null
+++ b/src/canvas-drm.h
@@ -0,0 +1,132 @@
+//
+// Copyright © 2012 Linaro Limited
+//
+// This file is part of the glmark2 OpenGL (ES) 2.0 benchmark.
+//
+// glmark2 is free software: you can redistribute it and/or modify it under the
+// terms of the GNU General Public License as published by the Free Software
+// Foundation, either version 3 of the License, or (at your option) any later
+// version.
+//
+// glmark2 is distributed in the hope that it will be useful, but WITHOUT ANY
+// WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
+// FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
+// details.
+//
+// You should have received a copy of the GNU General Public License along with
+// glmark2. If not, see <http://www.gnu.org/licenses/>.
+//
+// Authors:
+// Simon Que
+// Jesse Barker
+//
+#ifndef GLMARK2_CANVAS_DRM_H_
+#define GLMARK2_CANVAS_DRM_H_
+
+#include <cstring>
+#include <gbm.h>
+#include <drm.h>
+#include <xf86drm.h>
+#include <xf86drmMode.h>
+
+#include "canvas.h"
+#include "egl-state.h"
+
+struct DRMFBState
+{
+ int fd;
+ gbm_bo* bo;
+ uint32_t fb_id;
+};
+
+class DRMState
+{
+ static void page_flip_handler(int fd, unsigned int frame, unsigned int sec,
+ unsigned int usec, void* data);
+ static void fb_destroy_callback(gbm_bo* bo, void* data);
+ static void quit_handler(int signum);
+ static bool should_quit_;
+ DRMFBState* fb_get_from_bo(gbm_bo* bo);
+ bool init_gbm();
+ int fd_;
+ drmModeRes* resources_;
+ drmModeConnector* connector_;
+ drmModeEncoder* encoder_;
+ drmModeCrtcPtr crtc_;
+ drmModeModeInfo* mode_;
+ gbm_device* dev_;
+ gbm_surface* surface_;
+ gbm_bo* bo_;
+ DRMFBState* fb_;
+
+public:
+ DRMState() :
+ fd_(0),
+ resources_(0),
+ connector_(0),
+ encoder_(0),
+ mode_(0),
+ dev_(0),
+ surface_(0),
+ bo_(0),
+ fb_(0) {}
+ ~DRMState() { cleanup(); }
+ void cleanup();
+ bool init();
+ bool reset();
+ void do_flip();
+ bool should_quit() const { return should_quit_; }
+ gbm_device* device() const { return dev_; }
+ gbm_surface* surface() const { return surface_; }
+ unsigned int mode_width() const
+ {
+ if (mode_) {
+ return mode_->hdisplay;
+ }
+ return 0;
+ }
+ unsigned int mode_height() const
+ {
+ if (mode_) {
+ return mode_->vdisplay;
+ }
+ return 0;
+ }
+};
+
+/**
+ * Canvas for direct rendering with EGL.
+ */
+class CanvasDRM: public Canvas
+{
+public:
+ CanvasDRM(int width, int height) :
+ Canvas(width, height) {}
+ ~CanvasDRM();
+
+ virtual bool init();
+ virtual bool reset();
+ virtual void visible(bool visible);
+ virtual void clear();
+ virtual void update();
+ virtual void print_info();
+ virtual Pixel read_pixel(int x, int y);
+ virtual void write_to_file(std::string &filename);
+ virtual bool should_quit();
+ virtual void resize(int width, int height);
+
+protected:
+ virtual bool make_current();
+ virtual bool reset_context();
+ virtual void swap_buffers();
+ virtual bool supports_gl2();
+
+private:
+ DRMState drm_;
+ EGLState egl_;
+
+ void resize_no_viewport(int width, int height);
+ void init_gl_extensions();
+};
+
+#endif
diff --git a/src/main.cpp b/src/main.cpp
index 40a23d6..4402a64 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -35,7 +35,9 @@
#include <iostream>
#include <fstream>
-#if USE_GL
+#if USE_DRM
+#include "canvas-drm.h"
+#elif USE_GL
#include "canvas-x11-glx.h"
#elif USE_GLESv2
#include "canvas-x11-egl.h"
@@ -180,7 +182,9 @@ main(int argc, char *argv[])
}
// Create the canvas
-#if USE_GL
+#if USE_DRM
+ CanvasDRM canvas(Options::size.first, Options::size.second);
+#elif USE_GL
CanvasX11GLX canvas(Options::size.first, Options::size.second);
#elif USE_GLESv2
CanvasX11EGL canvas(Options::size.first, Options::size.second);
diff --git a/src/wscript_build b/src/wscript_build
index f0c233f..b742b48 100644
--- a/src/wscript_build
+++ b/src/wscript_build
@@ -4,6 +4,8 @@ common_sources = [f for f in all_sources if f.name.find('canvas-') == -1 and
f.name.find('egl-') == -1]
gl_sources = ['canvas-x11.cpp', 'canvas-x11-glx.cpp']
glesv2_sources = ['canvas-x11.cpp', 'canvas-x11-egl.cpp', 'egl-state.cpp']
+gl_drm_sources = ['canvas-drm.cpp', 'egl-state.cpp']
+glesv2_drm_sources = ['canvas-drm.cpp', 'egl-state.cpp']
libmatrix_sources = [f for f in bld.path.ant_glob('libmatrix/*.cc')
if not f.name.endswith('test.cc')]
includes = ['.', 'scene-ideas', 'scene-terrain']
@@ -47,3 +49,44 @@ if bld.env.USE_GLESv2:
includes = includes,
defines = ['USE_GLESv2', 'USE_EXCEPTIONS']
)
+
+if bld.env.USE_GL_DRM:
+ bld(
+ features = ['cxx', 'cxxstlib'],
+ source = libmatrix_sources,
+ target = 'matrix-drm',
+ lib = ['m'],
+ includes = ['.'],
+ export_includes = 'libmatrix',
+ defines = ['USE_DRM', '__GBM__', 'USE_GL', 'USE_EXCEPTIONS']
+ )
+ bld(
+ features = ['cxx', 'cprogram'],
+ source = common_sources + gl_drm_sources,
+ target = 'glmark2-drm',
+ use = ['egl', 'gl', 'matrix-drm', 'libpng12', 'drm', 'gbm'],
+ lib = ['m', 'jpeg', 'dl'],
+ includes = includes,
+ defines = ['USE_DRM', '__GBM__', 'USE_GL']
+ )
+
+if bld.env.USE_GLESv2_DRM:
+ bld(
+ features = ['cxx', 'cxxstlib'],
+ source = libmatrix_sources,
+ target = 'matrix-es2-drm',
+ lib = ['m'],
+ includes = ['.'],
+ export_includes = 'libmatrix',
+ defines = ['USE_DRM', '__GBM__', 'USE_GLESv2', 'USE_EXCEPTIONS']
+ )
+ bld(
+ features = ['cxx', 'cprogram'],
+ source = common_sources + glesv2_drm_sources,
+ target = 'glmark2-es2-drm',
+ use = ['egl', 'glesv2', 'matrix-es2-drm', 'libpng12', 'drm',
+ 'gbm'],
+ lib = ['m', 'jpeg', 'dl'],
+ includes = includes,
+ defines = ['USE_DRM', '__GBM__', 'USE_GLESv2']
+ )
diff --git a/wscript b/wscript
index 007eb0a..18cca76 100644
--- a/wscript
+++ b/wscript
@@ -20,6 +20,11 @@ def options(opt):
default = False, help='build using OpenGL 2.0')
opt.add_option('--enable-glesv2', action='store_true', dest = 'glesv2',
default = False, help='build using OpenGL ES 2.0')
+ opt.add_option('--enable-gl-drm', action='store_true', dest = 'gl_drm',
+ default = False, help='build using OpenGL 2.0 without X')
+ opt.add_option('--enable-glesv2-drm', action='store_true',
+ dest = 'glesv2_drm',
+ default = False, help='build using OpenGL ES 2.0 without X')
opt.add_option('--no-debug', action='store_false', dest = 'debug',
default = True, help='disable compiler debug information')
opt.add_option('--no-opt', action='store_false', dest = 'opt',
@@ -30,8 +35,10 @@ def options(opt):
help='path to additional data (models, shaders, textures)')
def configure(ctx):
- if not Options.options.gl and not Options.options.glesv2:
- ctx.fatal("You must configure using at least one of --enable-gl, --enable-glesv2")
+ if not Options.options.gl and not Options.options.glesv2 and \
+ not Options.options.gl_drm and not Options.options.glesv2_drm:
+ ctx.fatal("You must configure using at least one of --enable-gl, " +
+ "--enable-glesv2, --enable-gl-drm, --enable-glesv2-drm")
ctx.check_tool('gnu_dirs')
ctx.check_tool('compiler_cc')
@@ -54,15 +61,22 @@ def configure(ctx):
uselib = uselib, mandatory = True)
# Check required packages
- req_pkgs = [('x11', 'x11'), ('libpng12', 'libpng12')]
+ req_pkgs = [('libpng12', 'libpng12')]
for (pkg, uselib) in req_pkgs:
ctx.check_cfg(package = pkg, uselib_store = uselib,
args = '--cflags --libs', mandatory = True)
# Check optional packages
- opt_pkgs = [('gl', 'gl', Options.options.gl),
- ('egl', 'egl', Options.options.glesv2),
- ('glesv2', 'glesv2', Options.options.glesv2)]
+ opt_pkgs = [('x11', 'x11', Options.options.gl or Options.options.glesv2),
+ ('gl', 'gl', Options.options.gl or Options.options.gl_drm),
+ ('egl', 'egl', Options.options.glesv2 or
+ Options.options.glesv2_drm),
+ ('glesv2', 'glesv2', Options.options.glesv2 or
+ Options.options.glesv2_drm),
+ ('libdrm','drm', Options.options.gl_drm or
+ Options.options.glesv2_drm),
+ ('gbm','gbm', Options.options.gl_drm or
+ Options.options.glesv2_drm)]
for (pkg, uselib, mandatory) in opt_pkgs:
ctx.check_cfg(package = pkg, uselib_store = uselib,
args = '--cflags --libs', mandatory = mandatory)
@@ -94,6 +108,8 @@ def configure(ctx):
ctx.env.USE_GL = Options.options.gl
ctx.env.USE_GLESv2 = Options.options.glesv2
+ ctx.env.USE_GL_DRM = Options.options.gl_drm
+ ctx.env.USE_GLESv2_DRM = Options.options.glesv2_drm
ctx.msg("Prefix", ctx.env.PREFIX, color = 'PINK')
ctx.msg("Data path", data_path, color = 'PINK')
@@ -101,9 +117,13 @@ def configure(ctx):
color = 'PINK');
if ctx.env.HAVE_EXTRAS:
ctx.msg("Extras path", Options.options.extras_path, color = 'PINK')
- ctx.msg("Building GL2 version", "Yes" if ctx.env.USE_GL else "No",
+ ctx.msg("Building X11 GL2 version", "Yes" if ctx.env.USE_GL else "No",
color = 'PINK')
- ctx.msg("Building GLESv2 version", "Yes" if ctx.env.USE_GLESv2 else "No",
+ ctx.msg("Building X11 GLESv2 version", "Yes" if ctx.env.USE_GLESv2 else "No",
+ color = 'PINK')
+ ctx.msg("Building DRM GL2 version", "Yes" if ctx.env.USE_GL_DRM else "No",
+ color = 'PINK')
+ ctx.msg("Building DRM GLESv2 version", "Yes" if ctx.env.USE_GLESv2_DRM else "No",
color = 'PINK')
def build(ctx):