# HG changeset patch # User Paul Boddie # Date 1526684280 -7200 # Node ID fd9bc02853c617b40f273f208b7d10fa34cdd6b3 # Parent c5af0606a3d10a9a4116f5b724f25311cf3bb28d Introduced null event support for event loops, employed in the keypad servers. diff -r c5af0606a3d1 -r fd9bc02853c6 pkg/devices/keypad/include/keypad-event-loop.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/pkg/devices/keypad/include/keypad-event-loop.h Sat May 19 00:58:00 2018 +0200 @@ -0,0 +1,50 @@ +/* + * Keypad event loop functionality. + * + * (c) 2018 Paul Boddie + * + * This program 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 2 of + * the License, or (at your option) any later version. + * + * This program 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 this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, + * Boston, MA 02110-1301, USA + */ + +#pragma once + +#ifdef __cplusplus + +#include +#include + +/* Keypad event loop abstraction. */ + +class Keypad_event_loop : public Event_handler_loop +{ +public: + /* Initialise the event loop with a thread priority. */ + + explicit Keypad_event_loop(int priority=0x20) + : Event_handler_loop(priority) + { + } + + /* Event handler method. */ + + virtual void handle() + { + _handler(); + l4_sleep(20); /* 20ms -> 50Hz */ + } +}; + +#endif diff -r c5af0606a3d1 -r fd9bc02853c6 pkg/devices/keypad/src/letux400/keypad-letux400.cc --- a/pkg/devices/keypad/src/letux400/keypad-letux400.cc Fri May 18 23:41:51 2018 +0200 +++ b/pkg/devices/keypad/src/letux400/keypad-letux400.cc Sat May 19 00:58:00 2018 +0200 @@ -24,20 +24,13 @@ #include #include #include "keypad-server.h" +#include "keypad-event-loop.h" -#include -#include -#include - -#include #include #include -#include -#include #include #include -#include #include @@ -79,15 +72,26 @@ void *keymem = 0; -/* Thread details. */ + + +/* Set up access to memory. */ -static pthread_t _pthread; +static int setup_memory() +{ + if (get_memory("jz4730-gpio", &gpio_virt_base, &gpio_virt_base_end) < 0) + return 1; + + gpio_port_a = jz4730_gpio_init(gpio_virt_base, gpio_virt_base + 0x30, 32); + gpio_port_d = jz4730_gpio_init(gpio_virt_base + 0x90, gpio_virt_base + 0xc0, 32); + + return 0; +} /* Initialise the pins for scanning the keypad. */ -static void init_keyscan(void) +static void init_keyscan() { jz4730_gpio_multi_setup(gpio_port_a, &Jz4730_keypad_inputs_mask, Hw::Gpio_chip::Input, 0); jz4730_gpio_multi_config_pull(gpio_port_a, &Jz4730_keypad_inputs_mask, Hw::Gpio_chip::Pull_up); @@ -99,7 +103,7 @@ Store each column bitmap in the keypad array. */ -static void scan_keypad(void) +static void scan_keypad() { uint8_t column, row, value; @@ -122,54 +126,6 @@ (unsigned long) keypad + Jz4730_keypad_gpio_outputs_count); } -/* Set up access to memory. */ - -static int setup_memory(void) -{ - if (get_memory("jz4730-gpio", &gpio_virt_base, &gpio_virt_base_end) < 0) - return 1; - - gpio_port_a = jz4730_gpio_init(gpio_virt_base, gpio_virt_base + 0x30, 32); - gpio_port_d = jz4730_gpio_init(gpio_virt_base + 0x90, gpio_virt_base + 0xc0, 32); - - return 0; -} - - - -/* Worker thread for scanning the keypad. */ - -static void *scan_thread(void *data) -{ - (void) data; - - while (1) - { - scan_keypad(); - l4_sleep(20); /* 20ms -> 50Hz */ - } - - return 0; -} - -/* Thread initialisation. */ - -static int init_thread(void) -{ - pthread_attr_t thread_attr; - struct sched_param sp; - - if (pthread_attr_init(&thread_attr)) - return 1; - - sp.sched_priority = 0x20; - pthread_attr_setschedpolicy(&thread_attr, SCHED_L4); - pthread_attr_setschedparam(&thread_attr, &sp); - pthread_attr_setinheritsched(&thread_attr, PTHREAD_EXPLICIT_SCHED); - - return pthread_create(&_pthread, &thread_attr, scan_thread, 0); -} - static L4Re::Util::Registry_server<> server; @@ -199,7 +155,9 @@ /* Set up a thread to scan the keypad concurrently with the server loop. */ - init_thread(); + Keypad_event_loop loop; + loop.attach(scan_keypad); + loop.start(); /* Initialise and register a server object. */ diff -r c5af0606a3d1 -r fd9bc02853c6 pkg/devices/keypad/src/qi_lb60/keypad-qi_lb60.cc --- a/pkg/devices/keypad/src/qi_lb60/keypad-qi_lb60.cc Fri May 18 23:41:51 2018 +0200 +++ b/pkg/devices/keypad/src/qi_lb60/keypad-qi_lb60.cc Sat May 19 00:58:00 2018 +0200 @@ -24,17 +24,13 @@ #include #include #include "keypad-server.h" - -#include -#include -#include +#include "keypad-event-loop.h" #include #include #include #include -#include #include @@ -76,15 +72,26 @@ void *keymem = 0; -/* Thread details. */ + + +/* Set up access to memory. */ -static pthread_t _pthread; +static int setup_memory() +{ + if (get_memory("jz4740-gpio", &gpio_virt_base, &gpio_virt_base_end) < 0) + return 1; + + gpio_port_c = jz4740_gpio_init(gpio_virt_base + 0x200, gpio_virt_base + 0x300, 32); + gpio_port_d = jz4740_gpio_init(gpio_virt_base + 0x300, gpio_virt_base + 0x400, 32); + + return 0; +} /* Initialise the pins for scanning the keypad. */ -static void init_keyscan(void) +static void init_keyscan() { jz4740_gpio_multi_setup(gpio_port_d, &Jz4740_keypad_inputs_mask, Hw::Gpio_chip::Input, 0); jz4740_gpio_multi_config_pull(gpio_port_d, &Jz4740_keypad_inputs_mask, Hw::Gpio_chip::Pull_up); @@ -96,7 +103,7 @@ Store each column bitmap in the keypad array. */ -static void scan_keypad(void) +static void scan_keypad() { uint8_t column, row, value; @@ -119,54 +126,6 @@ (unsigned long) keypad + Jz4740_keypad_gpio_outputs_count); } -/* Set up access to memory. */ - -static int setup_memory(void) -{ - if (get_memory("jz4740-gpio", &gpio_virt_base, &gpio_virt_base_end) < 0) - return 1; - - gpio_port_c = jz4740_gpio_init(gpio_virt_base + 0x200, gpio_virt_base + 0x300, 32); - gpio_port_d = jz4740_gpio_init(gpio_virt_base + 0x300, gpio_virt_base + 0x400, 32); - - return 0; -} - - - -/* Worker thread for scanning the keypad. */ - -static void *scan_thread(void *data) -{ - (void) data; - - while (1) - { - scan_keypad(); - l4_sleep(20); /* 20ms -> 50Hz */ - } - - return 0; -} - -/* Thread initialisation. */ - -static int init_thread(void) -{ - pthread_attr_t thread_attr; - struct sched_param sp; - - if (pthread_attr_init(&thread_attr)) - return 1; - - sp.sched_priority = 0x20; - pthread_attr_setschedpolicy(&thread_attr, SCHED_L4); - pthread_attr_setschedparam(&thread_attr, &sp); - pthread_attr_setinheritsched(&thread_attr, PTHREAD_EXPLICIT_SCHED); - - return pthread_create(&_pthread, &thread_attr, scan_thread, 0); -} - static L4Re::Util::Registry_server<> server; @@ -196,7 +155,9 @@ /* Set up a thread to scan the keypad concurrently with the server loop. */ - init_thread(); + Keypad_event_loop loop; + loop.attach(scan_keypad); + loop.start(); /* Initialise and register a server object. */ diff -r c5af0606a3d1 -r fd9bc02853c6 pkg/devices/util/include/event-loop.h --- a/pkg/devices/util/include/event-loop.h Fri May 18 23:41:51 2018 +0200 +++ b/pkg/devices/util/include/event-loop.h Sat May 19 00:58:00 2018 +0200 @@ -93,4 +93,38 @@ } }; +/* Event loop with handler and null event type. */ + +template <> +class Event_handler_loop : public Event_loop +{ +protected: + /* Event type. */ + + typedef void Event_type; + + /* Handler function type. */ + + typedef void (*Event_handler)(); + + /* External handler function. */ + + Event_handler _handler; + +public: + /* Initialise the event loop with a thread priority. */ + + explicit Event_handler_loop(int priority=0x20) + : Event_loop(priority) + { + } + + /* Attach a handler to the loop. */ + + virtual void attach(Event_handler handler) + { + _handler = handler; + } +}; + #endif