diff --git a/repos/dde_linux/src/lib/usb/input/input_component.cc b/repos/dde_linux/src/lib/usb/input/input_component.cc
index e4d33ca1f..b553d9bb2 100644
--- a/repos/dde_linux/src/lib/usb/input/input_component.cc
+++ b/repos/dde_linux/src/lib/usb/input/input_component.cc
@@ -15,7 +15,7 @@
#include
#include
-#include
+#include
#include
#include
@@ -25,19 +25,27 @@
using namespace Genode;
-/*********************
- ** Input component **
- *********************/
+/**
+ * Return singleton instance of input-session component
+ */
+static Input::Session_component &input_session()
+{
+ static Input::Session_component inst;
+ return inst;
+}
-typedef Ring_buffer Input_ring_buffer;
-static Input_ring_buffer ev_queue;
-
-namespace Input {
-
- void event_handling(bool enable) { }
- bool event_pending() { return !ev_queue.empty(); }
- Event get_event() { return ev_queue.get(); }
+/**
+ * Return singleton instance of input-root component
+ *
+ * On the first call (from 'start_input_service'), the 'ep' argument is
+ * specified. All subsequent calls (from 'input_callback') just return the
+ * reference to the singleton instance.
+ */
+static Input::Root_component &input_root(Rpc_entrypoint *ep = 0)
+{
+ static Input::Root_component root(*ep, input_session());
+ return root;
}
@@ -58,20 +66,20 @@ static void input_callback(enum input_event_type type,
}
try {
- ev_queue.add(Input::Event(t, code,
- absolute_x, absolute_y,
- relative_x, relative_y));
- } catch (Input_ring_buffer::Overflow) {
+ input_session().submit(Input::Event(t, code,
+ absolute_x, absolute_y,
+ relative_x, relative_y));
+ } catch (Input::Event_queue::Overflow) {
PWRN("input ring buffer overflow");
}
}
-void start_input_service(void *ep)
+void start_input_service(void *ep_ptr)
{
- Rpc_entrypoint *e = static_cast(ep);
- static Input::Root input_root(e, env()->heap());
- env()->parent()->announce(e->manage(&input_root));
+ Rpc_entrypoint *ep = static_cast(ep_ptr);
+
+ env()->parent()->announce(ep->manage(&input_root(ep)));
genode_input_register(input_callback);
}
diff --git a/repos/demo/src/server/liquid_framebuffer/services.cc b/repos/demo/src/server/liquid_framebuffer/services.cc
index be9765e4b..f465b6524 100644
--- a/repos/demo/src/server/liquid_framebuffer/services.cc
+++ b/repos/demo/src/server/liquid_framebuffer/services.cc
@@ -11,77 +11,30 @@
* under the terms of the GNU General Public License version 2.
*/
+/* Genode include */
#include
#include
#include
#include
-#include
+#include
#include
#include
+#include
+/* local includes */
#include "services.h"
typedef Genode::Texture Texture_rgb565;
-/*****************
- ** Event queue **
- *****************/
-
-class Event_queue
+/**
+ * Return singleton instance of input session component
+ */
+Input::Session_component &input_session()
{
- private:
-
- enum { QUEUE_SIZE = 1024 };
-
- Input::Event _queue[QUEUE_SIZE];
- int _head;
- int _tail;
- Genode::Semaphore _sem;
-
- public:
-
- /**
- * Constructor
- */
- Event_queue(): _head(0), _tail(0)
- {
- Scout::memset(_queue, 0, sizeof(_queue));
- }
-
- void post(Input::Event ev)
- {
- if ((_head + 1)%QUEUE_SIZE != _tail) {
- _queue[_head] = ev;
- _head = (_head + 1)%QUEUE_SIZE;
- _sem.up();
- }
- }
-
- Input::Event get()
- {
- _sem.down();
- Input::Event dst_ev = _queue[_tail];
- _tail = (_tail + 1)%QUEUE_SIZE;
- return dst_ev;
- }
-
- int pending() { return _head != _tail; }
-
-} _ev_queue;
-
-
-/***************************
- ** Input service backend **
- ***************************/
-
-namespace Input {
-
- void event_handling(bool enable) { }
- bool event_pending() { return _ev_queue.pending(); }
- Event get_event() { return _ev_queue.get(); }
-
+ static Input::Session_component inst;
+ return inst;
}
@@ -93,16 +46,16 @@ class Window_content : public Scout::Element
{
private:
- Event_queue *_ev_queue;
- Scout::Point _old_mouse_position;
- Element *_element;
+ Input::Session_component &_input_session;
+ Scout::Point _old_mouse_position;
+ Element *_element;
public:
- Content_event_handler(Event_queue *ev_queue,
+ Content_event_handler(Input::Session_component &input_session,
Scout::Element *element)
:
- _ev_queue(ev_queue), _element(element) { }
+ _input_session(input_session),_element(element) { }
void handle(Scout::Event &ev)
{
@@ -123,10 +76,10 @@ class Window_content : public Scout::Element
: Input::Event::INVALID;
if (type != Input::Event::INVALID)
- _ev_queue->post(Input::Event(type, code, mouse_position.x(),
- mouse_position.y(),
- mouse_position.x() - _old_mouse_position.x(),
- mouse_position.y() - _old_mouse_position.y()));
+ _input_session.submit(Input::Event(type, code, mouse_position.x(),
+ mouse_position.y(),
+ mouse_position.x() - _old_mouse_position.x(),
+ mouse_position.y() - _old_mouse_position.y()));
_old_mouse_position = mouse_position;
}
@@ -173,9 +126,9 @@ class Window_content : public Scout::Element
};
- bool _config_alpha;
- Content_event_handler _ev_handler;
- Fb_texture *_fb;
+ bool _config_alpha;
+ Content_event_handler _ev_handler;
+ Fb_texture *_fb;
/**
* Size of the framebuffer handed out by the next call of 'dataspace'
@@ -198,11 +151,12 @@ class Window_content : public Scout::Element
public:
- Window_content(unsigned fb_w, unsigned fb_h, Event_queue *ev_queue,
+ Window_content(unsigned fb_w, unsigned fb_h,
+ Input::Session_component &input_session,
bool config_alpha)
:
_config_alpha(config_alpha),
- _ev_handler(ev_queue, this),
+ _ev_handler(input_session, this),
_fb(new (Genode::env()->heap()) Fb_texture(fb_w, fb_h, _config_alpha)),
_next_size(fb_w, fb_h),
_designated_size(_next_size)
@@ -268,76 +222,52 @@ Scout::Element *window_content() { return _window_content; }
** Implementation of the framebuffer service **
***********************************************/
-namespace Framebuffer
+namespace Framebuffer { class Session_component; }
+
+class Framebuffer::Session_component : public Genode::Rpc_object
{
- class Session_component : public Genode::Rpc_object
- {
- private:
+ private:
- Window_content &_window_content;
+ Window_content &_window_content;
- Genode::Signal_context_capability _sync_sigh;
+ Genode::Signal_context_capability _sync_sigh;
- public:
+ public:
- Session_component(Window_content &window_content)
- : _window_content(window_content) { }
+ Session_component(Window_content &window_content)
+ : _window_content(window_content) { }
- Genode::Dataspace_capability dataspace() override
- {
- _window_content.realloc_framebuffer();
- return _window_content.fb_ds_cap();
- }
+ Genode::Dataspace_capability dataspace() override
+ {
+ _window_content.realloc_framebuffer();
+ return _window_content.fb_ds_cap();
+ }
- Mode mode() const override
- {
- return Mode(_window_content.mode_size().w(),
- _window_content.mode_size().h(), Mode::RGB565);
- }
+ Mode mode() const override
+ {
+ return Mode(_window_content.mode_size().w(),
+ _window_content.mode_size().h(), Mode::RGB565);
+ }
- void mode_sigh(Genode::Signal_context_capability sigh) override {
- _window_content.mode_sigh(sigh); }
+ void mode_sigh(Genode::Signal_context_capability sigh) override {
+ _window_content.mode_sigh(sigh); }
- void sync_sigh(Genode::Signal_context_capability sigh) override {
- _sync_sigh = sigh; }
+ void sync_sigh(Genode::Signal_context_capability sigh) override {
+ _sync_sigh = sigh; }
- void refresh(int x, int y, int w, int h) override
- {
- _window_content.redraw_area(x, y, w, h);
+ void refresh(int x, int y, int w, int h) override
+ {
+ _window_content.redraw_area(x, y, w, h);
- if (_sync_sigh.valid())
- Genode::Signal_transmitter(_sync_sigh).submit();
- }
- };
-
-
- class Root : public Genode::Root_component
- {
- private:
-
- Window_content &_window_content;
-
- protected:
-
- Session_component *_create_session(const char *args) override {
- return new (md_alloc()) Session_component(_window_content); }
-
- public:
-
- Root(Genode::Rpc_entrypoint *session_ep,
- Genode::Allocator *md_alloc,
- Window_content &window_content)
- :
- Genode::Root_component(session_ep, md_alloc),
- _window_content(window_content)
- { }
- };
-}
+ if (_sync_sigh.valid())
+ Genode::Signal_transmitter(_sync_sigh).submit();
+ }
+};
void init_window_content(unsigned fb_w, unsigned fb_h, bool config_alpha)
{
- static Window_content content(fb_w, fb_h, &_ev_queue, config_alpha);
+ static Window_content content(fb_w, fb_h, input_session(), config_alpha);
_window_content = &content;
}
@@ -346,11 +276,10 @@ void init_services(Genode::Rpc_entrypoint &ep)
{
using namespace Genode;
- /*
- * Let the entry point serve the framebuffer and input root interfaces
- */
- static Framebuffer::Root fb_root(&ep, env()->heap(), *_window_content);
- static Input::Root input_root(&ep, env()->heap());
+ static Framebuffer::Session_component fb_session(*_window_content);
+ static Static_root fb_root(ep.manage(&fb_session));
+
+ static Input::Root_component input_root(ep, input_session());
/*
* Now, the root interfaces are ready to accept requests.
diff --git a/repos/gems/src/server/d3m/input_service.h b/repos/gems/src/server/d3m/input_service.h
index 771455f9e..4932afdd8 100644
--- a/repos/gems/src/server/d3m/input_service.h
+++ b/repos/gems/src/server/d3m/input_service.h
@@ -110,6 +110,14 @@ namespace Input {
* Flush input events
*/
Genode::size_t flush() { return _client.flush(); }
+
+ /**
+ * Register signal handler for input notifications
+ */
+ void sigh(Genode::Signal_context_capability sigh)
+ {
+ _client.sigh(sigh);
+ }
};
@@ -183,6 +191,12 @@ namespace Input {
}
return dst_count;
}
+
+ void sigh(Genode::Signal_context_capability sigh)
+ {
+ for (Source *e = _sources.first(); e; e = e->next())
+ e->sigh(sigh);
+ }
};
@@ -214,18 +228,23 @@ namespace Input {
** Input-session interface **
*****************************/
- Genode::Dataspace_capability dataspace() { return _ev_ds.cap(); }
+ Genode::Dataspace_capability dataspace() override { return _ev_ds.cap(); }
- bool is_pending() const
+ bool is_pending() const override
{
return _source_registry.any_source_has_pending_input();
}
- int flush()
+ int flush() override
{
return _source_registry.flush_sources(_ev_ds.local_addr(),
MAX_EVENTS);
}
+
+ void sigh(Genode::Signal_context_capability sigh) override
+ {
+ _source_registry.sigh(sigh);
+ }
};
/**
diff --git a/repos/libports/src/app/qt5/qt_avplay/control_bar.cpp b/repos/libports/src/app/qt5/qt_avplay/control_bar.cpp
index 2fb88fc6d..d40eff97c 100644
--- a/repos/libports/src/app/qt5/qt_avplay/control_bar.cpp
+++ b/repos/libports/src/app/qt5/qt_avplay/control_bar.cpp
@@ -17,22 +17,22 @@
/* Qoost includes */
#include
-#include "input_service.h"
+/* local includes */
#include "main_window.h"
void Control_bar::_rewind()
{
/* mouse click at horizontal position 0 */
- ev_queue.add(Input::Event(Input::Event::PRESS, Input::BTN_LEFT, 0, 0, 0, 0));
- ev_queue.add(Input::Event(Input::Event::RELEASE, Input::BTN_LEFT, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::PRESS, Input::BTN_LEFT, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::RELEASE, Input::BTN_LEFT, 0, 0, 0, 0));
}
void Control_bar::_pause_resume()
{
- ev_queue.add(Input::Event(Input::Event::PRESS, Input::KEY_SPACE, 0, 0, 0, 0));
- ev_queue.add(Input::Event(Input::Event::RELEASE, Input::KEY_SPACE, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::PRESS, Input::KEY_SPACE, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::RELEASE, Input::KEY_SPACE, 0, 0, 0, 0));
_playing = !_playing;
if (_playing)
@@ -51,8 +51,9 @@ void Control_bar::_stop()
}
-Control_bar::Control_bar()
-: _playing(true)
+Control_bar::Control_bar(Input::Event_queue &event_queue)
+:
+ _event_queue(event_queue), _playing(true)
{
update_style_id(_play_pause_button, "play");
diff --git a/repos/libports/src/app/qt5/qt_avplay/control_bar.h b/repos/libports/src/app/qt5/qt_avplay/control_bar.h
index 86f1afcf4..7a88ddf4f 100644
--- a/repos/libports/src/app/qt5/qt_avplay/control_bar.h
+++ b/repos/libports/src/app/qt5/qt_avplay/control_bar.h
@@ -22,6 +22,9 @@
#include
#include
+/* Genode includes */
+#include
+
struct Play_pause_button : QPushButton { Q_OBJECT };
struct Stop_button : QPushButton { Q_OBJECT };
struct Volume_label : QLabel { Q_OBJECT };
@@ -33,6 +36,8 @@ class Control_bar : public Compound_widget
private:
+ Input::Event_queue &_event_queue;
+
QMember _play_pause_button;
QMember _stop_button;
QMember _volume_label;
@@ -49,7 +54,7 @@ class Control_bar : public Compound_widget
public:
- Control_bar();
+ Control_bar(Input::Event_queue &event_queue);
Q_SIGNALS:
diff --git a/repos/libports/src/app/qt5/qt_avplay/input_service.cpp b/repos/libports/src/app/qt5/qt_avplay/input_service.cpp
deleted file mode 100644
index 65bb5a5c4..000000000
--- a/repos/libports/src/app/qt5/qt_avplay/input_service.cpp
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * \brief Input service
- * \author Christian Prochaska
- * \date 2012-03-29
- */
-
-/*
- * Copyright (C) 2012-2013 Genode Labs GmbH
- *
- * This file is part of the Genode OS framework, which is distributed
- * under the terms of the GNU General Public License version 2.
- */
-
-/* Genode includes */
-#include
-
-#include "input_service.h"
-
-using namespace Genode;
-
-Event_queue ev_queue;
-
-
-namespace Input {
-
- /*
- * Event handling is disabled on queue creation and will be enabled later if a
- * session is created.
- */
- void event_handling(bool enable)
- {
- if (enable)
- ev_queue.enable();
- else
- ev_queue.disable();
- }
-
- bool event_pending() { return !ev_queue.empty(); }
- Event get_event() { return ev_queue.get(); }
-}
diff --git a/repos/libports/src/app/qt5/qt_avplay/input_service.h b/repos/libports/src/app/qt5/qt_avplay/input_service.h
deleted file mode 100644
index 7612f2699..000000000
--- a/repos/libports/src/app/qt5/qt_avplay/input_service.h
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * \brief Input service
- * \author Christian Prochaska
- * \date 2012-03-29
- */
-
-/*
- * Copyright (C) 2012-2013 Genode Labs GmbH
- *
- * This file is part of the Genode OS framework, which is distributed
- * under the terms of the GNU General Public License version 2.
- */
-
-#ifndef _INPUT_SERVICE_H_
-#define _INPUT_SERVICE_H_
-
-/* Genode includes */
-#include
-
-extern Event_queue ev_queue;
-
-extern void create_input_service();
-
-#endif /* _INPUT_SERVICE_H_ */
diff --git a/repos/libports/src/app/qt5/qt_avplay/main.cpp b/repos/libports/src/app/qt5/qt_avplay/main.cpp
index 84a751adf..de37c2a27 100644
--- a/repos/libports/src/app/qt5/qt_avplay/main.cpp
+++ b/repos/libports/src/app/qt5/qt_avplay/main.cpp
@@ -17,6 +17,11 @@
/* qt_avplay includes */
#include "main_window.h"
+/* Genode includes */
+#include
+#include
+#include
+
static inline void load_stylesheet()
{
@@ -37,6 +42,14 @@ int main(int argc, char *argv[])
load_stylesheet();
+ /* look for dynamic linker */
+ try {
+ static Genode::Rom_connection ldso_rom("ld.lib.so");
+ Genode::Process::dynamic_linker(ldso_rom.dataspace());
+ } catch (...) {
+ PERR("ld.lib.so not found");
+ }
+
QMember main_window;
main_window->show();
diff --git a/repos/libports/src/app/qt5/qt_avplay/main_window.cpp b/repos/libports/src/app/qt5/qt_avplay/main_window.cpp
index 163dd9ded..1659206aa 100644
--- a/repos/libports/src/app/qt5/qt_avplay/main_window.cpp
+++ b/repos/libports/src/app/qt5/qt_avplay/main_window.cpp
@@ -11,17 +11,10 @@
* under the terms of the GNU General Public License version 2.
*/
-/* Genode includes */
-#include
-#include
-#include
-#include
-
/* qt_avplay includes */
#include "avplay_policy.h"
#include "filter_framebuffer_policy.h"
#include "framebuffer_root.h"
-#include "input_service.h"
#include "main_window.h"
@@ -30,49 +23,23 @@ using namespace Genode;
struct Framebuffer_filter
{
- enum { MAX_FILTER_NAME_SIZE = 32 };
- char name[MAX_FILTER_NAME_SIZE];
- Genode::Number_of_bytes ram_quota;
+ enum { MAX_FILTER_NAME_SIZE = 32 };
+ char name[MAX_FILTER_NAME_SIZE];
+ Genode::Number_of_bytes ram_quota;
- Service_registry *framebuffer_out_registry;
- Rpc_entrypoint *ep;
- Filter_framebuffer_policy *policy;
- Slave *slave;
+ Service_registry *framebuffer_out_registry;
+ Rpc_entrypoint *ep;
+ Filter_framebuffer_policy *policy;
+ Slave *slave;
};
Main_window::Main_window()
+:
+ _control_bar(_input_session.event_queue())
{
- /* look for dynamic linker */
-
- try {
- static Rom_connection ldso_rom("ld.lib.so");
- Process::dynamic_linker(ldso_rom.dataspace());
- } catch (...) {
- PERR("ld.lib.so not found");
- }
-
- /* get the name of the media file from the config file */
- enum { MAX_LEN_MEDIAFILE_NAME = 256 };
- static char mediafile[MAX_LEN_MEDIAFILE_NAME] = "mediafile";
- try {
- config()->xml_node().sub_node("mediafile").attribute("name").value(mediafile, sizeof(mediafile));
- } catch(...) {
- PWRN("no config node found, using \"mediafile\"");
- }
-
- /* create local services */
-
- enum { STACK_SIZE = 2*sizeof(addr_t)*1024 };
- static Cap_connection cap;
- static Rpc_entrypoint avplay_ep(&cap, STACK_SIZE, "avplay_ep");
- static Service_registry input_registry;
- static Service_registry nitpicker_framebuffer_registry;
-
- static Input::Root input_root(&avplay_ep, env()->heap());
- static Local_service input_service(Input::Session::service_name(), &input_root);
- input_registry.insert(&input_service);
- avplay_ep.manage(&input_root);
+ _input_registry.insert(&_input_service);
+ _ep.manage(&_input_root);
/* find out which filtering framebuffer services to start and sort them in reverse order */
@@ -90,15 +57,15 @@ Main_window::Main_window()
/* start the filtering framebuffer services */
- Service_registry *framebuffer_in_registry = &nitpicker_framebuffer_registry;
+ Service_registry *framebuffer_in_registry = &_nitpicker_framebuffer_registry;
Q_FOREACH(Framebuffer_filter *framebuffer_filter, framebuffer_filters) {
framebuffer_filter->framebuffer_out_registry = new Service_registry;
- framebuffer_filter->ep = new Rpc_entrypoint(&cap, STACK_SIZE, "filter_fb_ep");
+ framebuffer_filter->ep = new Rpc_entrypoint(&_cap, STACK_SIZE, "filter_fb_ep");
framebuffer_filter->policy = new Filter_framebuffer_policy(framebuffer_filter->name,
*framebuffer_filter->ep,
- *framebuffer_in_registry,
- *framebuffer_filter->framebuffer_out_registry);
+ *framebuffer_in_registry,
+ *framebuffer_filter->framebuffer_out_registry);
framebuffer_filter->slave = new Slave(*framebuffer_filter->ep,
*framebuffer_filter->policy,
framebuffer_filter->ram_quota);
@@ -106,17 +73,17 @@ Main_window::Main_window()
}
Rpc_entrypoint *local_framebuffer_ep = framebuffer_filters.isEmpty() ?
- &avplay_ep :
+ &_ep :
framebuffer_filters.at(0)->ep;
static Framebuffer::Root framebuffer_root(local_framebuffer_ep, env()->heap(), *_avplay_widget, 640, 480);
static Local_service framebuffer_service(Framebuffer::Session::service_name(), &framebuffer_root);
- nitpicker_framebuffer_registry.insert(&framebuffer_service);
+ _nitpicker_framebuffer_registry.insert(&framebuffer_service);
/* start avplay */
- static Avplay_policy avplay_policy(avplay_ep, input_registry, *framebuffer_in_registry, mediafile);
- static Genode::Slave avplay_slave(avplay_ep, avplay_policy, 32*1024*1024);
+ static Avplay_policy avplay_policy(_ep, _input_registry, *framebuffer_in_registry, _mediafile_name.buf);
+ static Genode::Slave avplay_slave(_ep, avplay_policy, 32*1024*1024);
/* add widgets to layout */
diff --git a/repos/libports/src/app/qt5/qt_avplay/main_window.h b/repos/libports/src/app/qt5/qt_avplay/main_window.h
index aaf869922..0b10b58cd 100644
--- a/repos/libports/src/app/qt5/qt_avplay/main_window.h
+++ b/repos/libports/src/app/qt5/qt_avplay/main_window.h
@@ -23,6 +23,14 @@
#include
#include
+/* Genode includes */
+#include
+#include
+#include
+#include
+#include
+
+/* local includes */
#include "control_bar.h"
@@ -32,6 +40,35 @@ class Main_window : public Compound_widget
private:
+ struct Mediafile_name
+ {
+ /* get the name of the media file from the config file */
+ enum { MAX_LEN_MEDIAFILE_NAME = 256 };
+ char buf[MAX_LEN_MEDIAFILE_NAME];
+
+ Mediafile_name()
+ {
+ Genode::strncpy(buf, "mediafile", sizeof(buf));
+ try {
+ Genode::config()->xml_node().sub_node("mediafile")
+ .attribute("name").value(buf, sizeof(buf));
+ } catch(...) {
+ PWRN("no config node found, using \"mediafile\"");
+ }
+ }
+ } _mediafile_name;
+
+ enum { STACK_SIZE = 2*sizeof(Genode::addr_t)*1024 };
+ Genode::Cap_connection _cap;
+ Genode::Rpc_entrypoint _ep { &_cap, STACK_SIZE, "avplay_ep" };
+ Genode::Service_registry _input_registry;
+ Genode::Service_registry _nitpicker_framebuffer_registry;
+
+ Input::Session_component _input_session;
+ Input::Root_component _input_root { _ep, _input_session };
+
+ Genode::Local_service _input_service { Input::Session::service_name(), &_input_root };
+
QMember _avplay_widget;
QMember _control_bar;
diff --git a/repos/libports/src/app/qt5/qt_avplay/qt_avplay.pro b/repos/libports/src/app/qt5/qt_avplay/qt_avplay.pro
index 8b9dc41c5..5c2c7d9d1 100644
--- a/repos/libports/src/app/qt5/qt_avplay/qt_avplay.pro
+++ b/repos/libports/src/app/qt5/qt_avplay/qt_avplay.pro
@@ -6,7 +6,6 @@ HEADERS = avplay_policy.h \
main_window.h
SOURCES = control_bar.cpp \
framebuffer_session_component.cc \
- input_service.cpp \
main.cpp \
main_window.cpp
RESOURCES = style.qrc
diff --git a/repos/os/include/input/component.h b/repos/os/include/input/component.h
index 06de55761..3fceef878 100644
--- a/repos/os/include/input/component.h
+++ b/repos/os/include/input/component.h
@@ -17,100 +17,61 @@
#include
#include
#include
+#include
#include
#include
-#include
+#include
-namespace Input {
+namespace Input { class Session_component; }
- /********************
- ** Input back end **
- ********************/
+class Input::Session_component : public Genode::Rpc_object
+{
+ private:
- /**
- * Enable/disable input event handling
- *
- * \param enable enable (true) or disable (false) back end
- *
- * The front end informs the back end about when to start capturing input
- * events for an open session. Later, the back end may be deactivated on
- * session destruction.
- */
- void event_handling(bool enable);
+ Genode::Attached_ram_dataspace _ds { Genode::env()->ram_session(),
+ Event_queue::QUEUE_SIZE*sizeof(Input::Event) };
- /**
- * Check if an event is pending
- */
- bool event_pending();
+ Event_queue _event_queue;
- /**
- * Wait for an event, Zzz...zz..
- */
- Input::Event get_event();
+ public:
+
+ /**
+ * Return reference to event queue of the session
+ */
+ Event_queue &event_queue() { return _event_queue; }
+
+ /**
+ * Submit input event to event queue
+ *
+ * \throw Input::Event_queue::Overflow
+ */
+ void submit(Input::Event event) { _event_queue.add(event); }
- /*****************************
- ** Input service front end **
- *****************************/
+ /******************************
+ ** Input::Session interface **
+ ******************************/
- class Session_component : public Genode::Rpc_object
- {
- private:
+ Genode::Dataspace_capability dataspace() override { return _ds.cap(); }
- /*
- * Input event buffer that is shared with the client
- */
- enum { MAX_EVENTS = 1000 };
+ bool is_pending() const override { return !_event_queue.empty(); }
- Genode::Attached_ram_dataspace _ev_ds;
+ int flush() override
+ {
+ Input::Event *dst = _ds.local_addr();
+
+ unsigned cnt = 0;
+ for (; cnt < Event_queue::QUEUE_SIZE && !_event_queue.empty(); cnt++)
+ *dst++ = _event_queue.get();
- public:
+ return cnt;
+ }
- Session_component()
- : _ev_ds(Genode::env()->ram_session(), MAX_EVENTS*sizeof(Event)) {
- event_handling(true); }
-
- ~Session_component() {
- event_handling(false); }
-
- Genode::Dataspace_capability dataspace() { return _ev_ds.cap(); }
-
- bool is_pending() const { return event_pending(); }
-
- int flush()
- {
- /* dump events into event buffer dataspace */
- int i;
- Input::Event *ev_ds_buf = _ev_ds.local_addr();
- for (i = 0; (i < MAX_EVENTS) && event_pending(); ++i)
- ev_ds_buf[i] = get_event();
-
- /* return number of flushed events */
- return i;
- }
- };
-
-
- /**
- * Shortcut for single-client root component
- */
- typedef Genode::Root_component Root_component;
-
-
- class Root : public Root_component
- {
- protected:
-
- Session_component *_create_session(const char *args) {
- return new (md_alloc()) Session_component(); }
-
- public:
-
- Root(Genode::Rpc_entrypoint *session_ep,
- Genode::Allocator *md_alloc)
- : Root_component(session_ep, md_alloc) { }
- };
-}
+ void sigh(Genode::Signal_context_capability sigh) override
+ {
+ _event_queue.sigh(sigh);
+ }
+};
#endif /* _INCLUDE__INPUT__COMPONENT_H_ */
diff --git a/repos/os/include/input/event_queue.h b/repos/os/include/input/event_queue.h
index 82dbe0b5a..262de0984 100644
--- a/repos/os/include/input/event_queue.h
+++ b/repos/os/include/input/event_queue.h
@@ -5,7 +5,7 @@
*/
/*
- * Copyright (C) 2007-2013 Genode Labs GmbH
+ * Copyright (C) 2007-2014 Genode Labs GmbH
*
* This file is part of the Genode OS framework, which is distributed
* under the terms of the GNU General Public License version 2.
@@ -14,57 +14,70 @@
#ifndef _EVENT_QUEUE_H_
#define _EVENT_QUEUE_H_
-#include
+#include
#include
#include
-/**
- * Input event queue
- *
- * We expect the client to fetch events circa each 10ms. The PS/2 driver queues
- * up to 255 events, which should be enough. Normally, PS/2 generates not more
- * than 16Kbit/s, which would correspond to ca. 66 mouse events per 10ms.
- */
-class Event_queue
+namespace Input { class Event_queue; };
+
+
+class Input::Event_queue
{
+ public:
+
+ /**
+ * Input event queue
+ *
+ * We expect the client to fetch events circa each 10ms. The PS/2 driver
+ * queues up to 255 events, which should be enough. Normally, PS/2
+ * generates not more than 16Kbit/s, which would correspond to ca. 66 mouse
+ * events per 10ms.
+ */
+ enum { QUEUE_SIZE = 512U };
+
private:
- bool _enabled;
- Ring_buffer _ev_queue;
+ Ring_buffer _queue;
+
+ bool _enabled = false;
+
+ Genode::Signal_context_capability _sigh;
public:
- Event_queue() : _enabled(false), _ev_queue() { }
+ typedef typename Ring_buffer::Overflow Overflow;
- void enable() { _enabled = true; }
- void disable() { _enabled = false; }
+ void enabled(bool enabled) { _enabled = enabled; }
- void add(Input::Event e)
+ bool enabled() const { return _enabled; }
+
+ void sigh(Genode::Signal_context_capability sigh) { _sigh = sigh; }
+
+ void submit_signal()
{
- if (!_enabled) return;
-
- try {
- _ev_queue.add(e);
- } catch (Ring_buffer::Overflow) {
- PWRN("event buffer overflow");
- }
+ if (_sigh.valid())
+ Genode::Signal_transmitter(_sigh).submit();
}
- Input::Event get()
+ /**
+ * \throw Overflow
+ */
+ void add(Input::Event ev, bool submit_signal_immediately = true)
{
- if (_enabled)
- return _ev_queue.get();
- else
- return Input::Event();
+ if (!_enabled)
+ return;
+
+ _queue.add(ev);
+
+ if (submit_signal_immediately)
+ submit_signal();
}
- bool empty()
- {
- if (_enabled)
- return _ev_queue.empty();
- else
- return true;
- }
+ Input::Event get() { return _queue.get(); }
+
+ bool empty() const { return _queue.empty(); }
+
+ int avail_capacity() const { return _queue.avail_capacity(); }
};
#endif /* _EVENT_QUEUE_H_ */
diff --git a/repos/os/include/input/root.h b/repos/os/include/input/root.h
new file mode 100644
index 000000000..78a658a8c
--- /dev/null
+++ b/repos/os/include/input/root.h
@@ -0,0 +1,70 @@
+/*
+ * \brief Input root component
+ * \author Norman Feske
+ * \date 2014-05-31
+ */
+
+/*
+ * Copyright (C) 2014 Genode Labs GmbH
+ *
+ * This file is part of the Genode OS framework, which is distributed
+ * under the terms of the GNU General Public License version 2.
+ */
+
+#ifndef _INPUT__ROOT_H_
+#define _INPUT__ROOT_H_
+
+/* Genode includes */
+#include
+#include
+
+
+namespace Input { class Root_component; }
+
+/*
+ * This input root component tracks if the session has been opened. If a client
+ * is connected, the 'Event_queue::enabled' gets enabled. This is useful to
+ * omit the enqueuing of input events into the event queue before any client is
+ * interested in receiving input events. If we would not drop such early input
+ * events, the queue might overflow when input events are generated at boot
+ * times.
+ */
+class Input::Root_component : public Genode::Static_root
+{
+ private:
+
+ Genode::Rpc_entrypoint &_ep;
+ Input::Session_component &_session;
+
+ public:
+
+ Root_component(Genode::Rpc_entrypoint &ep, Input::Session_component &session)
+ :
+ Static_root(ep.manage(&session)),
+ _ep(ep), _session(session)
+ { }
+
+ ~Root_component()
+ {
+ _ep.dissolve(&_session);
+ }
+
+ Genode::Capability
+ session(Genode::Root::Session_args const &args,
+ Genode::Affinity const &affinity) override
+ {
+ if (_session.event_queue().enabled())
+ throw Root::Unavailable();
+
+ _session.event_queue().enabled(true);
+
+ return Static_root::session(args, affinity);
+ }
+
+ void close(Genode::Capability)
+ {
+ _session.event_queue().enabled(false);
+ }
+};
+
+#endif /* _INPUT__ROOT_H_ */
diff --git a/repos/os/include/input_session/client.h b/repos/os/include/input_session/client.h
index 42e47d5c4..2577b4b96 100644
--- a/repos/os/include/input_session/client.h
+++ b/repos/os/include/input_session/client.h
@@ -24,14 +24,17 @@ namespace Input {
explicit Session_client(Session_capability session)
: Genode::Rpc_client(session) { }
- Genode::Dataspace_capability dataspace() {
+ Genode::Dataspace_capability dataspace() override {
return call(); }
- bool is_pending() const {
+ bool is_pending() const override {
return call(); }
- int flush() {
+ int flush() override {
return call(); }
+
+ void sigh(Genode::Signal_context_capability sigh) override {
+ call(sigh); }
};
}
diff --git a/repos/os/include/input_session/input_session.h b/repos/os/include/input_session/input_session.h
index e9489b41c..9b48f6a27 100644
--- a/repos/os/include/input_session/input_session.h
+++ b/repos/os/include/input_session/input_session.h
@@ -17,6 +17,7 @@
#include
#include
#include
+#include
namespace Input {
@@ -45,6 +46,11 @@ namespace Input {
*/
virtual int flush() = 0;
+ /**
+ * Register signal handler to be notified on arrival of new input
+ */
+ virtual void sigh(Genode::Signal_context_capability) = 0;
+
/*********************
** RPC declaration **
@@ -53,8 +59,9 @@ namespace Input {
GENODE_RPC(Rpc_dataspace, Genode::Dataspace_capability, dataspace);
GENODE_RPC(Rpc_is_pending, bool, is_pending);
GENODE_RPC(Rpc_flush, int, flush);
+ GENODE_RPC(Rpc_sigh, void, sigh, Genode::Signal_context_capability);
- GENODE_RPC_INTERFACE(Rpc_dataspace, Rpc_is_pending, Rpc_flush);
+ GENODE_RPC_INTERFACE(Rpc_dataspace, Rpc_is_pending, Rpc_flush, Rpc_sigh);
};
}
diff --git a/repos/os/src/drivers/framebuffer/sdl/fb_sdl.cc b/repos/os/src/drivers/framebuffer/sdl/fb_sdl.cc
index 15bb575d5..e61b05bc2 100644
--- a/repos/os/src/drivers/framebuffer/sdl/fb_sdl.cc
+++ b/repos/os/src/drivers/framebuffer/sdl/fb_sdl.cc
@@ -19,10 +19,12 @@
#include
#include
#include
-#include
#include
#include
-#include
+#include
+
+/* local includes */
+#include
/*
@@ -44,85 +46,63 @@ static void *fb_ds_addr;
** Implementation of the framebuffer service **
***********************************************/
-namespace Framebuffer {
+namespace Framebuffer { class Session_component; }
- class Session_component : public Genode::Rpc_object
- {
- private:
+class Framebuffer::Session_component : public Genode::Rpc_object
+{
+ private:
- Mode _mode;
+ Mode _mode;
- Genode::Signal_context_capability _sync_sigh;
+ Genode::Signal_context_capability _sync_sigh;
- public:
+ public:
- /**
- * Constructor
- */
- Session_component() : _mode(scr_width, scr_height, Mode::RGB565) { }
+ /**
+ * Constructor
+ */
+ Session_component() : _mode(scr_width, scr_height, Mode::RGB565) { }
- Genode::Dataspace_capability dataspace() override { return fb_ds_cap; }
+ Genode::Dataspace_capability dataspace() override { return fb_ds_cap; }
- Mode mode() const override { return _mode; }
+ Mode mode() const override { return _mode; }
- void mode_sigh(Genode::Signal_context_capability) override { }
+ void mode_sigh(Genode::Signal_context_capability) override { }
- void sync_sigh(Genode::Signal_context_capability sigh) override
- {
- _sync_sigh = sigh;
+ void sync_sigh(Genode::Signal_context_capability sigh) override
+ {
+ _sync_sigh = sigh;
+ }
+
+ void refresh(int x, int y, int w, int h) override
+ {
+ /* clip refresh area to screen boundaries */
+ int x1 = Genode::max(x, 0);
+ int y1 = Genode::max(y, 0);
+ int x2 = Genode::min(x + w - 1, scr_width - 1);
+ int y2 = Genode::min(y + h - 1, scr_height - 1);
+
+ if (x1 <= x2 && y1 <= y2) {
+
+ /* copy pixels from shared dataspace to sdl surface */
+ const int start_offset = _mode.bytes_per_pixel()*(y1*scr_width + x1);
+ const int line_len = _mode.bytes_per_pixel()*(x2 - x1 + 1);
+ const int pitch = _mode.bytes_per_pixel()*scr_width;
+
+ char *src = (char *)fb_ds_addr + start_offset;
+ char *dst = (char *)screen->pixels + start_offset;
+
+ for (int i = y1; i <= y2; i++, src += pitch, dst += pitch)
+ Genode::memcpy(dst, src, line_len);
+
+ /* flush pixels in sdl window */
+ SDL_UpdateRect(screen, x1, y1, x2 - x1 + 1, y2 - y1 + 1);
}
- void refresh(int x, int y, int w, int h) override
- {
- /* clip refresh area to screen boundaries */
- int x1 = Genode::max(x, 0);
- int y1 = Genode::max(y, 0);
- int x2 = Genode::min(x + w - 1, scr_width - 1);
- int y2 = Genode::min(y + h - 1, scr_height - 1);
-
- if (x1 <= x2 && y1 <= y2) {
-
- /* copy pixels from shared dataspace to sdl surface */
- const int start_offset = _mode.bytes_per_pixel()*(y1*scr_width + x1);
- const int line_len = _mode.bytes_per_pixel()*(x2 - x1 + 1);
- const int pitch = _mode.bytes_per_pixel()*scr_width;
-
- char *src = (char *)fb_ds_addr + start_offset;
- char *dst = (char *)screen->pixels + start_offset;
-
- for (int i = y1; i <= y2; i++, src += pitch, dst += pitch)
- Genode::memcpy(dst, src, line_len);
-
- /* flush pixels in sdl window */
- SDL_UpdateRect(screen, x1, y1, x2 - x1 + 1, y2 - y1 + 1);
- }
-
- if (_sync_sigh.valid())
- Genode::Signal_transmitter(_sync_sigh).submit();
- }
- };
-
-
- /**
- * Shortcut for single-client root component
- */
- typedef Genode::Root_component Root_component;
-
-
- class Root : public Root_component
- {
- protected:
-
- Session_component *_create_session(const char *args) override {
- return new (md_alloc()) Session_component(); }
-
- public:
-
- Root(Genode::Rpc_entrypoint *session_ep,
- Genode::Allocator *md_alloc)
- : Root_component(session_ep, md_alloc) { }
- };
-}
+ if (_sync_sigh.valid())
+ Genode::Signal_transmitter(_sync_sigh).submit();
+ }
+};
/**
@@ -172,19 +152,21 @@ extern "C" int main(int, char**)
static Cap_connection cap;
static Rpc_entrypoint ep(&cap, STACK_SIZE, "fb_ep");
- /*
- * Let the entry point serve the framebuffer and input root interfaces
- */
- static Framebuffer::Root framebuffer_root(&ep, env()->heap());
- static Input::Root input_root(&ep, env()->heap());
+ static Input::Session_component input_session;
+ static Input::Root_component input_root(ep, input_session);
+
+ static Framebuffer::Session_component fb_session;
+ static Static_root fb_root(ep.manage(&fb_session));
/*
* Now, the root interfaces are ready to accept requests.
* This is the right time to tell mummy about our services.
*/
- env()->parent()->announce(ep.manage(&framebuffer_root));
+ env()->parent()->announce(ep.manage(&fb_root));
env()->parent()->announce(ep.manage(&input_root));
- sleep_forever();
+ for (;;)
+ input_session.submit(wait_for_event());
+
return 0;
}
diff --git a/repos/os/src/drivers/framebuffer/sdl/input.cc b/repos/os/src/drivers/framebuffer/sdl/input.cc
index 99e21ce44..65e5be90a 100644
--- a/repos/os/src/drivers/framebuffer/sdl/input.cc
+++ b/repos/os/src/drivers/framebuffer/sdl/input.cc
@@ -16,12 +16,11 @@
/* Genode */
#include
-
-/* Local */
-#include
-
#include
+/* local */
+#include
+
/**
* Convert SDL keycode to Genode keycode
*/
@@ -139,14 +138,7 @@ static long convert_keycode(int sdl_keycode)
};
-void Input::event_handling(bool enable) { }
-bool Input::event_pending() { return SDL_PollEvent(0); }
-
-
-/**
- * Wait for an event, Zzz...zz..
- */
-Input::Event Input::get_event()
+Input::Event wait_for_event()
{
using namespace Input;
diff --git a/repos/os/src/drivers/framebuffer/sdl/input.h b/repos/os/src/drivers/framebuffer/sdl/input.h
new file mode 100644
index 000000000..4b52c2440
--- /dev/null
+++ b/repos/os/src/drivers/framebuffer/sdl/input.h
@@ -0,0 +1,24 @@
+/*
+ * \brief SDL input support
+ * \author Norman Feske
+ * \date 2006-08-16
+ */
+
+/*
+ * Copyright (C) 2006-2013 Genode Labs GmbH
+ *
+ * This file is part of the Genode OS framework, which is distributed
+ * under the terms of the GNU General Public License version 2.
+ */
+
+#ifndef _INPUT_H_
+#define _INPUT_H_
+
+#include
+
+/**
+ * Wait for an event, Zzz...zz..
+ */
+Input::Event wait_for_event();
+
+#endif /* _INPUT_H_ */
diff --git a/repos/os/src/drivers/framebuffer/sdl/target.mk b/repos/os/src/drivers/framebuffer/sdl/target.mk
index df89f8cf2..33f046170 100644
--- a/repos/os/src/drivers/framebuffer/sdl/target.mk
+++ b/repos/os/src/drivers/framebuffer/sdl/target.mk
@@ -3,13 +3,4 @@ LIBS = lx_hybrid
REQUIRES = linux sdl
SRC_CC = fb_sdl.cc input.cc
LX_LIBS = sdl
-
-#
-# Explicitly add host headers to the include-search location. Even though this
-# path happens to be added via the 'lx_hybrid' library via the 'HOST_INC_DIR'
-# variable, we want to give /usr/include preference for resolving 'SDL/*'
-# headers. Otherwise, if libSDL is prepared in 'libports', the build system
-# would pull-in the SDL headers from libports.
-#
-INC_DIR += /usr/include
-
+INC_DIR += $(PRG_DIR)
diff --git a/repos/os/src/drivers/input/dummy/main.cc b/repos/os/src/drivers/input/dummy/main.cc
index a460baeb0..4e5d5c313 100644
--- a/repos/os/src/drivers/input/dummy/main.cc
+++ b/repos/os/src/drivers/input/dummy/main.cc
@@ -15,6 +15,7 @@
/* Genode */
#include
#include
+#include
#include
#include
#include
@@ -41,15 +42,17 @@ namespace Input {
{
public:
- Dataspace_capability dataspace() { return ev_ds_cap; }
+ Dataspace_capability dataspace() override { return ev_ds_cap; }
- bool is_pending() const { return 0; }
+ bool is_pending() const override { return 0; }
- int flush()
+ int flush() override
{
/* return number of flushed events */
return 0;
}
+
+ void sigh(Genode::Signal_context_capability) override { }
};
diff --git a/repos/os/src/drivers/input/imx53/main.cc b/repos/os/src/drivers/input/imx53/main.cc
index 56076d9eb..9d3444f55 100644
--- a/repos/os/src/drivers/input/imx53/main.cc
+++ b/repos/os/src/drivers/input/imx53/main.cc
@@ -13,41 +13,21 @@
* under the terms of the GNU General Public License version 2.
*/
-/* Genode */
+/* Genode includes */
#include
#include
#include
-#include
#include
#include
#include
+#include
#include
+/* local includes */
#include
using namespace Genode;
-static Event_queue ev_queue;
-
-namespace Input {
-
- /*
- * Event handling is disabled on queue creation and will be enabled later if a
- * session is created.
- */
- void event_handling(bool enable)
- {
- if (enable)
- ev_queue.enable();
- else
- ev_queue.disable();
- }
-
- bool event_pending() { return !ev_queue.empty(); }
- Event get_event() { return ev_queue.get(); }
-}
-
-
int main(int argc, char **argv)
{
/* initialize server entry point */
@@ -55,23 +35,25 @@ int main(int argc, char **argv)
static Cap_connection cap;
static Rpc_entrypoint ep(&cap, STACK_SIZE, "input_ep");
+ static Input::Session_component session;
+
Platform::Connection plat_drv;
switch (plat_drv.revision()) {
case Platform::Session::SMD:
plat_drv.enable(Platform::Session::I2C_2);
plat_drv.enable(Platform::Session::I2C_3);
plat_drv.enable(Platform::Session::BUTTONS);
- Input::Tablet_driver::factory(ev_queue);
+ Input::Tablet_driver::factory(session.event_queue());
break;
default:
PWRN("No input driver available for this board");
}
/* entry point serving input root interface */
- static Input::Root input_root(&ep, env()->heap());
+ static Input::Root_component root(ep, session);
/* tell parent about the service */
- env()->parent()->announce(ep.manage(&input_root));
+ env()->parent()->announce(ep.manage(&root));
/* main's done - go to sleep */
sleep_forever();
diff --git a/repos/os/src/drivers/input/ps2/pl050/main.cc b/repos/os/src/drivers/input/ps2/pl050/main.cc
index c69dccf11..58eb59cc0 100644
--- a/repos/os/src/drivers/input/ps2/pl050/main.cc
+++ b/repos/os/src/drivers/input/ps2/pl050/main.cc
@@ -11,12 +11,15 @@
* under the terms of the GNU General Public License version 2.
*/
+/* Genode includes */
#include
#include
#include
#include
+#include
#include
+/* local includes */
#include "ps2_keyboard.h"
#include "ps2_mouse.h"
#include "irq_handler.h"
@@ -24,26 +27,6 @@
using namespace Genode;
-static Event_queue ev_queue;
-
-namespace Input {
-
- /*
- * Event handling is disabled on queue creation and will be enabled later if a
- * session is created.
- */
- void event_handling(bool enable)
- {
- if (enable)
- ev_queue.enable();
- else
- ev_queue.disable();
- }
-
- bool event_pending() { return !ev_queue.empty(); }
- Event get_event() { return ev_queue.get(); }
-}
-
int main(int argc, char **argv)
{
@@ -52,12 +35,6 @@ int main(int argc, char **argv)
Serial_interface *kbd = pl050.kbd_interface();
Serial_interface *aux = pl050.aux_interface();
- Ps2_mouse ps2_mouse(*aux, ev_queue);
- Ps2_keyboard ps2_keybd(*kbd, ev_queue, true);
-
- Irq_handler ps2_mouse_irq(PL050_MOUSE_IRQ, aux, ps2_mouse);
- Irq_handler ps2_keybd_irq(PL050_KEYBD_IRQ, kbd, ps2_keybd);
-
/*
* Initialize server entry point
*/
@@ -65,11 +42,19 @@ int main(int argc, char **argv)
static Cap_connection cap;
static Rpc_entrypoint ep(&cap, STACK_SIZE, "ps2_ep");
+ static Input::Session_component session;
+ static Input::Root_component root(ep, session);
+
+ Ps2_mouse ps2_mouse(*aux, session.event_queue());
+ Ps2_keyboard ps2_keybd(*kbd, session.event_queue(), true);
+
+ Irq_handler ps2_mouse_irq(PL050_MOUSE_IRQ, aux, ps2_mouse);
+ Irq_handler ps2_keybd_irq(PL050_KEYBD_IRQ, kbd, ps2_keybd);
+
/*
* Let the entry point serve the input root interface
*/
- static Input::Root input_root(&ep, env()->heap());
- env()->parent()->announce(ep.manage(&input_root));
+ env()->parent()->announce(ep.manage(&root));
Genode::sleep_forever();
return 0;
diff --git a/repos/os/src/drivers/input/ps2/ps2_keyboard.h b/repos/os/src/drivers/input/ps2/ps2_keyboard.h
index d62147f1c..f4a059a7b 100644
--- a/repos/os/src/drivers/input/ps2/ps2_keyboard.h
+++ b/repos/os/src/drivers/input/ps2/ps2_keyboard.h
@@ -30,9 +30,9 @@ class Ps2_keyboard : public Input_driver
static const bool verbose = false;
static const bool verbose_scan_codes = false;
- Serial_interface &_kbd;
- Event_queue &_ev_queue;
- bool _xlate_mode;
+ Serial_interface &_kbd;
+ Input::Event_queue &_ev_queue;
+ bool _xlate_mode;
/**
* Array for tracking the current keyboard state
@@ -363,7 +363,7 @@ class Ps2_keyboard : public Input_driver
* If 'xlate_mode' is true, we do not attempt to manually switch the
* keyboard to scan code set 2 but just decode the scan-code set 1.
*/
- Ps2_keyboard(Serial_interface &kbd, Event_queue &ev_queue, bool xlate_mode)
+ Ps2_keyboard(Serial_interface &kbd, Input::Event_queue &ev_queue, bool xlate_mode)
:
_kbd(kbd), _ev_queue(ev_queue), _xlate_mode(xlate_mode)
{
diff --git a/repos/os/src/drivers/input/ps2/ps2_mouse.h b/repos/os/src/drivers/input/ps2/ps2_mouse.h
index 23860cd55..7896a47bb 100644
--- a/repos/os/src/drivers/input/ps2/ps2_mouse.h
+++ b/repos/os/src/drivers/input/ps2/ps2_mouse.h
@@ -71,12 +71,12 @@ class Ps2_mouse : public Input_driver
static const bool verbose = false;
- Serial_interface &_aux;
- Event_queue &_ev_queue;
+ Serial_interface &_aux;
+ Input::Event_queue &_ev_queue;
- Type _type;
+ Type _type;
- bool _button_state[NUM_BUTTONS];
+ bool _button_state[NUM_BUTTONS];
unsigned char _packet[MAX_PACKET_LEN];
int _packet_len;
@@ -149,9 +149,10 @@ class Ps2_mouse : public Input_driver
public:
- Ps2_mouse(Serial_interface &aux, Event_queue &ev_queue)
+ Ps2_mouse(Serial_interface &aux, Input::Event_queue &ev_queue)
:
- _aux(aux), _ev_queue(ev_queue), _type(PS2),
+ _aux(aux),
+ _ev_queue(ev_queue), _type(PS2),
_packet_len(PS2_PACKET_LEN), _packet_idx(0)
{
for (unsigned i = 0; i < NUM_BUTTONS; ++i)
diff --git a/repos/os/src/drivers/input/ps2/x86/main.cc b/repos/os/src/drivers/input/ps2/x86/main.cc
index 2fb90e812..5760bc18e 100644
--- a/repos/os/src/drivers/input/ps2/x86/main.cc
+++ b/repos/os/src/drivers/input/ps2/x86/main.cc
@@ -15,6 +15,7 @@
#include
#include
#include
+#include
#include
#include "i8042.h"
@@ -24,26 +25,6 @@
using namespace Genode;
-static Event_queue ev_queue;
-
-namespace Input {
-
- /*
- * Event handling is disabled on queue creation and will be enabled later if a
- * session is created.
- */
- void event_handling(bool enable)
- {
- if (enable)
- ev_queue.enable();
- else
- ev_queue.disable();
- }
-
- bool event_pending() { return !ev_queue.empty(); }
- Event get_event() { return ev_queue.get(); }
-}
-
int main(int argc, char **argv)
{
@@ -52,24 +33,23 @@ int main(int argc, char **argv)
Serial_interface *kbd = i8042.kbd_interface();
Serial_interface *aux = i8042.aux_interface();
- Ps2_mouse ps2_mouse(*aux, ev_queue);
- Ps2_keyboard ps2_keybd(*kbd, ev_queue, i8042.kbd_xlate());
+ /*
+ * Initialize server entry point
+ */
+ enum { STACK_SIZE = 4096 };
+ static Cap_connection cap;
+ static Rpc_entrypoint ep(&cap, STACK_SIZE, "ps2_ep");
+
+ static Input::Session_component session;
+ static Input::Root_component root(ep, session);
+
+ Ps2_mouse ps2_mouse(*aux, session.event_queue());
+ Ps2_keyboard ps2_keybd(*kbd, session.event_queue(), i8042.kbd_xlate());
Irq_handler ps2_mouse_irq(12, ps2_mouse);
Irq_handler ps2_keybd_irq( 1, ps2_keybd);
- /*
- * Initialize server entry point
- */
- enum { STACK_SIZE = sizeof(addr_t)*1024 };
- static Cap_connection cap;
- static Rpc_entrypoint ep(&cap, STACK_SIZE, "ps2_ep");
-
- /*
- * Let the entry point serve the input root interface
- */
- static Input::Root input_root(&ep, env()->heap());
- env()->parent()->announce(ep.manage(&input_root));
+ env()->parent()->announce(ep.manage(&root));
Genode::sleep_forever();
return 0;
diff --git a/repos/os/src/server/loader/input.h b/repos/os/src/server/loader/input.h
index 76ab5d4b1..762a9b7d5 100644
--- a/repos/os/src/server/loader/input.h
+++ b/repos/os/src/server/loader/input.h
@@ -66,11 +66,11 @@ namespace Input {
** Input session interface **
*****************************/
- Dataspace_capability dataspace() { return _real_input.dataspace(); }
+ Dataspace_capability dataspace() override { return _real_input.dataspace(); }
- bool is_pending() const { return _real_input.is_pending(); }
+ bool is_pending() const override { return _real_input.is_pending(); }
- int flush()
+ int flush() override
{
/* translate mouse position to child's coordinate system */
Transformer::Delta delta = _transformer.delta();
@@ -97,6 +97,11 @@ namespace Input {
return num_ev;
}
+
+ void sigh(Signal_context_capability sigh) override
+ {
+ _real_input.sigh(sigh);
+ }
};
}
diff --git a/repos/os/src/server/nit_fb/main.cc b/repos/os/src/server/nit_fb/main.cc
index b1bc2e59d..8631b5af8 100644
--- a/repos/os/src/server/nit_fb/main.cc
+++ b/repos/os/src/server/nit_fb/main.cc
@@ -82,11 +82,11 @@ namespace Input {
** Input session interface **
*****************************/
- Genode::Dataspace_capability dataspace() { return _to_input_ds; }
+ Genode::Dataspace_capability dataspace() override { return _to_input_ds; }
- bool is_pending() const { return _from_input->is_pending(); }
+ bool is_pending() const override { return _from_input->is_pending(); }
- int flush()
+ int flush() override
{
/* flush events at input session */
int num_events = _from_input->flush();
@@ -103,6 +103,11 @@ namespace Input {
}
return num_events;
}
+
+ void sigh(Genode::Signal_context_capability sigh) override
+ {
+ _from_input->sigh(sigh);
+ }
};
}
diff --git a/repos/os/src/server/nitpicker/main.cc b/repos/os/src/server/nitpicker/main.cc
index d161d0fc8..3ff257fcc 100644
--- a/repos/os/src/server/nitpicker/main.cc
+++ b/repos/os/src/server/nitpicker/main.cc
@@ -257,8 +257,19 @@ class Input::Session_component : public Genode::Rpc_object
Event _ev_buf[MAX_EVENTS];
unsigned _num_ev = 0;
+ Signal_context_capability _sigh;
+
public:
+ /**
+ * Wake up client
+ */
+ void submit_signal()
+ {
+ if (_sigh.valid())
+ Signal_transmitter(_sigh).submit();
+ }
+
/**
* Enqueue event into local event buffer of the input session
*/
@@ -269,6 +280,8 @@ class Input::Session_component : public Genode::Rpc_object
/* insert event into local event buffer */
_ev_buf[_num_ev++] = *ev;
+
+ submit_signal();
}
@@ -276,11 +289,11 @@ class Input::Session_component : public Genode::Rpc_object
** Input session interface **
*****************************/
- Dataspace_capability dataspace() { return _ev_ram_ds.cap(); }
+ Dataspace_capability dataspace() override { return _ev_ram_ds.cap(); }
- bool is_pending() const { return _num_ev > 0; }
+ bool is_pending() const override { return _num_ev > 0; }
- int flush()
+ int flush() override
{
unsigned ev_cnt;
@@ -292,6 +305,8 @@ class Input::Session_component : public Genode::Rpc_object
_num_ev = 0;
return ev_cnt;
}
+
+ void sigh(Genode::Signal_context_capability sigh) override { _sigh = sigh; }
};
diff --git a/repos/qt4/src/app/qt_avplay/avplay_policy.h b/repos/qt4/src/app/qt_avplay/avplay_policy.h
index 1bcb30df9..958938275 100644
--- a/repos/qt4/src/app/qt_avplay/avplay_policy.h
+++ b/repos/qt4/src/app/qt_avplay/avplay_policy.h
@@ -54,6 +54,25 @@ class Avplay_policy : public QObject, public Genode::Slave_policy
arg1_node.setAttribute("value", _mediafile);
config_node.appendChild(arg1_node);
+ /*
+ * Configure libc of avplay to direct output to LOG and to obtain
+ * the mediafile from ROM.
+ */
+ QDomElement libc_node = config_doc.createElement("libc");
+ libc_node.setAttribute("stdout", "/dev/log");
+ libc_node.setAttribute("stderr", "/dev/log");
+ QDomElement libc_vfs_node = config_doc.createElement("vfs");
+ QDomElement libc_vfs_dev_node = config_doc.createElement("dir");
+ libc_vfs_dev_node.setAttribute("name", "dev");
+ QDomElement libc_vfs_dev_log_node = config_doc.createElement("log");
+ libc_vfs_dev_node.appendChild(libc_vfs_dev_log_node);
+ libc_vfs_node.appendChild(libc_vfs_dev_node);
+ QDomElement libc_vfs_mediafile_node = config_doc.createElement("rom");
+ libc_vfs_mediafile_node.setAttribute("name", "mediafile");
+ libc_vfs_node.appendChild(libc_vfs_mediafile_node);
+ libc_node.appendChild(libc_vfs_node);
+ config_node.appendChild(libc_node);
+
QDomElement sdl_audio_volume_node = config_doc.createElement("sdl_audio_volume");
sdl_audio_volume_node.setAttribute("value", QString::number(_sdl_audio_volume));
config_node.appendChild(sdl_audio_volume_node);
diff --git a/repos/qt4/src/app/qt_avplay/control_bar.cpp b/repos/qt4/src/app/qt_avplay/control_bar.cpp
index 2fb88fc6d..d40eff97c 100644
--- a/repos/qt4/src/app/qt_avplay/control_bar.cpp
+++ b/repos/qt4/src/app/qt_avplay/control_bar.cpp
@@ -17,22 +17,22 @@
/* Qoost includes */
#include
-#include "input_service.h"
+/* local includes */
#include "main_window.h"
void Control_bar::_rewind()
{
/* mouse click at horizontal position 0 */
- ev_queue.add(Input::Event(Input::Event::PRESS, Input::BTN_LEFT, 0, 0, 0, 0));
- ev_queue.add(Input::Event(Input::Event::RELEASE, Input::BTN_LEFT, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::PRESS, Input::BTN_LEFT, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::RELEASE, Input::BTN_LEFT, 0, 0, 0, 0));
}
void Control_bar::_pause_resume()
{
- ev_queue.add(Input::Event(Input::Event::PRESS, Input::KEY_SPACE, 0, 0, 0, 0));
- ev_queue.add(Input::Event(Input::Event::RELEASE, Input::KEY_SPACE, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::PRESS, Input::KEY_SPACE, 0, 0, 0, 0));
+ _event_queue.add(Input::Event(Input::Event::RELEASE, Input::KEY_SPACE, 0, 0, 0, 0));
_playing = !_playing;
if (_playing)
@@ -51,8 +51,9 @@ void Control_bar::_stop()
}
-Control_bar::Control_bar()
-: _playing(true)
+Control_bar::Control_bar(Input::Event_queue &event_queue)
+:
+ _event_queue(event_queue), _playing(true)
{
update_style_id(_play_pause_button, "play");
diff --git a/repos/qt4/src/app/qt_avplay/control_bar.h b/repos/qt4/src/app/qt_avplay/control_bar.h
index f4420ebe9..6bb9af57b 100644
--- a/repos/qt4/src/app/qt_avplay/control_bar.h
+++ b/repos/qt4/src/app/qt_avplay/control_bar.h
@@ -21,6 +21,9 @@
#include
#include
+/* Genode includes */
+#include
+
struct Play_pause_button : QPushButton { Q_OBJECT };
struct Stop_button : QPushButton { Q_OBJECT };
struct Volume_label : QLabel { Q_OBJECT };
@@ -32,6 +35,8 @@ class Control_bar : public Compound_widget
private:
+ Input::Event_queue &_event_queue;
+
QMember _play_pause_button;
QMember _stop_button;
QMember _volume_label;
@@ -48,7 +53,7 @@ class Control_bar : public Compound_widget
public:
- Control_bar();
+ Control_bar(Input::Event_queue &event_queue);
Q_SIGNALS:
diff --git a/repos/qt4/src/app/qt_avplay/input_service.cpp b/repos/qt4/src/app/qt_avplay/input_service.cpp
deleted file mode 100644
index 65bb5a5c4..000000000
--- a/repos/qt4/src/app/qt_avplay/input_service.cpp
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * \brief Input service
- * \author Christian Prochaska
- * \date 2012-03-29
- */
-
-/*
- * Copyright (C) 2012-2013 Genode Labs GmbH
- *
- * This file is part of the Genode OS framework, which is distributed
- * under the terms of the GNU General Public License version 2.
- */
-
-/* Genode includes */
-#include
-
-#include "input_service.h"
-
-using namespace Genode;
-
-Event_queue ev_queue;
-
-
-namespace Input {
-
- /*
- * Event handling is disabled on queue creation and will be enabled later if a
- * session is created.
- */
- void event_handling(bool enable)
- {
- if (enable)
- ev_queue.enable();
- else
- ev_queue.disable();
- }
-
- bool event_pending() { return !ev_queue.empty(); }
- Event get_event() { return ev_queue.get(); }
-}
diff --git a/repos/qt4/src/app/qt_avplay/input_service.h b/repos/qt4/src/app/qt_avplay/input_service.h
deleted file mode 100644
index 7612f2699..000000000
--- a/repos/qt4/src/app/qt_avplay/input_service.h
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * \brief Input service
- * \author Christian Prochaska
- * \date 2012-03-29
- */
-
-/*
- * Copyright (C) 2012-2013 Genode Labs GmbH
- *
- * This file is part of the Genode OS framework, which is distributed
- * under the terms of the GNU General Public License version 2.
- */
-
-#ifndef _INPUT_SERVICE_H_
-#define _INPUT_SERVICE_H_
-
-/* Genode includes */
-#include
-
-extern Event_queue ev_queue;
-
-extern void create_input_service();
-
-#endif /* _INPUT_SERVICE_H_ */
diff --git a/repos/qt4/src/app/qt_avplay/main.cpp b/repos/qt4/src/app/qt_avplay/main.cpp
index 84a751adf..de37c2a27 100644
--- a/repos/qt4/src/app/qt_avplay/main.cpp
+++ b/repos/qt4/src/app/qt_avplay/main.cpp
@@ -17,6 +17,11 @@
/* qt_avplay includes */
#include "main_window.h"
+/* Genode includes */
+#include
+#include
+#include
+
static inline void load_stylesheet()
{
@@ -37,6 +42,14 @@ int main(int argc, char *argv[])
load_stylesheet();
+ /* look for dynamic linker */
+ try {
+ static Genode::Rom_connection ldso_rom("ld.lib.so");
+ Genode::Process::dynamic_linker(ldso_rom.dataspace());
+ } catch (...) {
+ PERR("ld.lib.so not found");
+ }
+
QMember main_window;
main_window->show();
diff --git a/repos/qt4/src/app/qt_avplay/main_window.cpp b/repos/qt4/src/app/qt_avplay/main_window.cpp
index 163dd9ded..1659206aa 100644
--- a/repos/qt4/src/app/qt_avplay/main_window.cpp
+++ b/repos/qt4/src/app/qt_avplay/main_window.cpp
@@ -11,17 +11,10 @@
* under the terms of the GNU General Public License version 2.
*/
-/* Genode includes */
-#include
-#include
-#include
-#include
-
/* qt_avplay includes */
#include "avplay_policy.h"
#include "filter_framebuffer_policy.h"
#include "framebuffer_root.h"
-#include "input_service.h"
#include "main_window.h"
@@ -30,49 +23,23 @@ using namespace Genode;
struct Framebuffer_filter
{
- enum { MAX_FILTER_NAME_SIZE = 32 };
- char name[MAX_FILTER_NAME_SIZE];
- Genode::Number_of_bytes ram_quota;
+ enum { MAX_FILTER_NAME_SIZE = 32 };
+ char name[MAX_FILTER_NAME_SIZE];
+ Genode::Number_of_bytes ram_quota;
- Service_registry *framebuffer_out_registry;
- Rpc_entrypoint *ep;
- Filter_framebuffer_policy *policy;
- Slave *slave;
+ Service_registry *framebuffer_out_registry;
+ Rpc_entrypoint *ep;
+ Filter_framebuffer_policy *policy;
+ Slave *slave;
};
Main_window::Main_window()
+:
+ _control_bar(_input_session.event_queue())
{
- /* look for dynamic linker */
-
- try {
- static Rom_connection ldso_rom("ld.lib.so");
- Process::dynamic_linker(ldso_rom.dataspace());
- } catch (...) {
- PERR("ld.lib.so not found");
- }
-
- /* get the name of the media file from the config file */
- enum { MAX_LEN_MEDIAFILE_NAME = 256 };
- static char mediafile[MAX_LEN_MEDIAFILE_NAME] = "mediafile";
- try {
- config()->xml_node().sub_node("mediafile").attribute("name").value(mediafile, sizeof(mediafile));
- } catch(...) {
- PWRN("no config node found, using \"mediafile\"");
- }
-
- /* create local services */
-
- enum { STACK_SIZE = 2*sizeof(addr_t)*1024 };
- static Cap_connection cap;
- static Rpc_entrypoint avplay_ep(&cap, STACK_SIZE, "avplay_ep");
- static Service_registry input_registry;
- static Service_registry nitpicker_framebuffer_registry;
-
- static Input::Root input_root(&avplay_ep, env()->heap());
- static Local_service input_service(Input::Session::service_name(), &input_root);
- input_registry.insert(&input_service);
- avplay_ep.manage(&input_root);
+ _input_registry.insert(&_input_service);
+ _ep.manage(&_input_root);
/* find out which filtering framebuffer services to start and sort them in reverse order */
@@ -90,15 +57,15 @@ Main_window::Main_window()
/* start the filtering framebuffer services */
- Service_registry *framebuffer_in_registry = &nitpicker_framebuffer_registry;
+ Service_registry *framebuffer_in_registry = &_nitpicker_framebuffer_registry;
Q_FOREACH(Framebuffer_filter *framebuffer_filter, framebuffer_filters) {
framebuffer_filter->framebuffer_out_registry = new Service_registry;
- framebuffer_filter->ep = new Rpc_entrypoint(&cap, STACK_SIZE, "filter_fb_ep");
+ framebuffer_filter->ep = new Rpc_entrypoint(&_cap, STACK_SIZE, "filter_fb_ep");
framebuffer_filter->policy = new Filter_framebuffer_policy(framebuffer_filter->name,
*framebuffer_filter->ep,
- *framebuffer_in_registry,
- *framebuffer_filter->framebuffer_out_registry);
+ *framebuffer_in_registry,
+ *framebuffer_filter->framebuffer_out_registry);
framebuffer_filter->slave = new Slave(*framebuffer_filter->ep,
*framebuffer_filter->policy,
framebuffer_filter->ram_quota);
@@ -106,17 +73,17 @@ Main_window::Main_window()
}
Rpc_entrypoint *local_framebuffer_ep = framebuffer_filters.isEmpty() ?
- &avplay_ep :
+ &_ep :
framebuffer_filters.at(0)->ep;
static Framebuffer::Root framebuffer_root(local_framebuffer_ep, env()->heap(), *_avplay_widget, 640, 480);
static Local_service framebuffer_service(Framebuffer::Session::service_name(), &framebuffer_root);
- nitpicker_framebuffer_registry.insert(&framebuffer_service);
+ _nitpicker_framebuffer_registry.insert(&framebuffer_service);
/* start avplay */
- static Avplay_policy avplay_policy(avplay_ep, input_registry, *framebuffer_in_registry, mediafile);
- static Genode::Slave avplay_slave(avplay_ep, avplay_policy, 32*1024*1024);
+ static Avplay_policy avplay_policy(_ep, _input_registry, *framebuffer_in_registry, _mediafile_name.buf);
+ static Genode::Slave avplay_slave(_ep, avplay_policy, 32*1024*1024);
/* add widgets to layout */
diff --git a/repos/qt4/src/app/qt_avplay/main_window.h b/repos/qt4/src/app/qt_avplay/main_window.h
index aaf869922..0b10b58cd 100644
--- a/repos/qt4/src/app/qt_avplay/main_window.h
+++ b/repos/qt4/src/app/qt_avplay/main_window.h
@@ -23,6 +23,14 @@
#include
#include
+/* Genode includes */
+#include
+#include
+#include
+#include
+#include
+
+/* local includes */
#include "control_bar.h"
@@ -32,6 +40,35 @@ class Main_window : public Compound_widget
private:
+ struct Mediafile_name
+ {
+ /* get the name of the media file from the config file */
+ enum { MAX_LEN_MEDIAFILE_NAME = 256 };
+ char buf[MAX_LEN_MEDIAFILE_NAME];
+
+ Mediafile_name()
+ {
+ Genode::strncpy(buf, "mediafile", sizeof(buf));
+ try {
+ Genode::config()->xml_node().sub_node("mediafile")
+ .attribute("name").value(buf, sizeof(buf));
+ } catch(...) {
+ PWRN("no config node found, using \"mediafile\"");
+ }
+ }
+ } _mediafile_name;
+
+ enum { STACK_SIZE = 2*sizeof(Genode::addr_t)*1024 };
+ Genode::Cap_connection _cap;
+ Genode::Rpc_entrypoint _ep { &_cap, STACK_SIZE, "avplay_ep" };
+ Genode::Service_registry _input_registry;
+ Genode::Service_registry _nitpicker_framebuffer_registry;
+
+ Input::Session_component _input_session;
+ Input::Root_component _input_root { _ep, _input_session };
+
+ Genode::Local_service _input_service { Input::Session::service_name(), &_input_root };
+
QMember _avplay_widget;
QMember _control_bar;
diff --git a/repos/qt4/src/app/qt_avplay/qt_avplay.pro b/repos/qt4/src/app/qt_avplay/qt_avplay.pro
index 8b9dc41c5..5c2c7d9d1 100644
--- a/repos/qt4/src/app/qt_avplay/qt_avplay.pro
+++ b/repos/qt4/src/app/qt_avplay/qt_avplay.pro
@@ -6,7 +6,6 @@ HEADERS = avplay_policy.h \
main_window.h
SOURCES = control_bar.cpp \
framebuffer_session_component.cc \
- input_service.cpp \
main.cpp \
main_window.cpp
RESOURCES = style.qrc
diff --git a/repos/qt4/src/app/qt_avplay/target.mk b/repos/qt4/src/app/qt_avplay/target.mk
index d60ce481b..6515e9be5 100644
--- a/repos/qt4/src/app/qt_avplay/target.mk
+++ b/repos/qt4/src/app/qt_avplay/target.mk
@@ -6,4 +6,4 @@ include $(QT4_REP_DIR)/src/app/tmpl/target_defaults.inc
include $(QT4_REP_DIR)/src/app/tmpl/target_final.inc
-LIBS += qnitpickerviewwidget
+LIBS += qnitpickerviewwidget qoost