chiark / gitweb /
Add support for operating GPIO lines through libgpiod.
authorBen Harris <bjh21@bjh21.me.uk>
Thu, 22 Nov 2018 23:46:46 +0000 (23:46 +0000)
committerBen Harris <bjh21@bjh21.me.uk>
Sat, 8 Dec 2018 22:30:09 +0000 (22:30 +0000)
Untested, since the Raspberry Pi at my disposal doesn't yet have
libgpiod.

Makefile
clunk.c

index 7d4839efa5c322eac4436e82ff17847a3a519907..387c3ab91b60d31831cf1d3544dfc8f9efe77a49 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1 +1,3 @@
-LDLIBS=-lrt
+all: clunk
+LDLIBS+=-lrt $$(pkg-config --libs libgpiod)
+CFLAGS+=$$(pkg-config --cflags libgpiod)
diff --git a/clunk.c b/clunk.c
index c6b847a3c9a8885793d403480789119906226a53..1879e708d363a001636fa4e44e94b81b14289afa 100644 (file)
--- a/clunk.c
+++ b/clunk.c
@@ -1,6 +1,7 @@
 #include <err.h>
 #include <errno.h>
 #include <fcntl.h>
+#include <gpiod.h>
 #include <signal.h>
 #include <stdbool.h>
 #include <stdio.h>
@@ -53,6 +54,19 @@ dummy_out(bool state)
                fflush(stdout);
        }
 }
+
+static struct gpiod_line *libgpiod_line;
+
+static void
+libgpiod_out(bool state)
+{
+
+       if (gpiod_line_set_value(libgpiod_line, state) == -1)
+               err(1, "gpiod_line_set_value");
+}
+
+static void (*outfn)(bool) = &dummy_out;
+
 static void
 record_tick()
 {
@@ -88,12 +102,12 @@ pulse()
 
        if (sigprocmask(SIG_BLOCK, &signals_to_block, &saved_mask) != 0)
                err(1, "sigprocmask(block)");
-       dummy_out(true);
+       (*outfn)(true);
        record_tick();
        errno = clock_nanosleep(CLOCK_MONOTONIC, 0, &ts, NULL);
        if (errno != 0)
                err(1, "clock_nanosleep");
-       dummy_out(false);
+       (*outfn)(false);
        if (sigprocmask(SIG_SETMASK, &saved_mask, NULL) != 0)
                err(1, "sigprocmask(restore)");
 }
@@ -124,6 +138,17 @@ init_statefile(char const *statefilename)
        }
 }
 
+static void
+init_libgpiod(char const *gpio_name)
+{
+
+       libgpiod_line = gpiod_line_find(gpio_name);
+       if (libgpiod_line == NULL)
+               err(1, "GPIO line '%s'", gpio_name);
+       if (gpiod_line_request_output(libgpiod_line, "clunk", false) == -1)
+               err(1, "requesting '%s'", gpio_name);
+}
+
 static void
 alrm_handler(int signo)
 {
@@ -160,7 +185,7 @@ init(int argc, char **argv)
        if (localtime_r(&ts.tv_sec, &displayed) == NULL)
                err(1, "localtime_r");
        displayed.tm_sec = (displayed.tm_sec >= 30) ? 30 : 0;
-       while ((opt = getopt(argc, argv, "f:s:")) != -1) {
+       while ((opt = getopt(argc, argv, "f:g:s:")) != -1) {
                switch (opt) {
                case 'f':
                        statefile = optarg;
@@ -168,6 +193,9 @@ init(int argc, char **argv)
                case 's':
                        statestr = optarg;
                        break;
+               case 'g':
+                       init_libgpiod(optarg);
+                       break;
                }
        }
        if (statefile != NULL)