new file mode 100644
@@ -0,0 +1,9 @@
+# SPDX-License-Identifier: GPL-2.0-or-later
+# SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+gpiodetectcxx
+gpiofindcxx
+gpiogetcxx
+gpioinfocxx
+gpiomoncxx
+gpiosetcxx
new file mode 100644
@@ -0,0 +1,26 @@
+# SPDX-License-Identifier: GPL-2.0-or-later
+# SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+AM_CPPFLAGS = -I$(top_srcdir)/bindings/cxx/ -I$(top_srcdir)/include
+AM_CPPFLAGS += -Wall -Wextra -g -std=gnu++17
+AM_LDFLAGS = -lgpiodcxx -L$(top_builddir)/bindings/cxx/
+
+noinst_PROGRAMS = \
+ gpiodetectcxx \
+ gpiofindcxx \
+ gpiogetcxx \
+ gpioinfocxx \
+ gpiomoncxx \
+ gpiosetcxx
+
+gpiodetectcxx_SOURCES = gpiodetectcxx.cpp
+
+gpiofindcxx_SOURCES = gpiofindcxx.cpp
+
+gpiogetcxx_SOURCES = gpiogetcxx.cpp
+
+gpioinfocxx_SOURCES = gpioinfocxx.cpp
+
+gpiomoncxx_SOURCES = gpiomoncxx.cpp
+
+gpiosetcxx_SOURCES = gpiosetcxx.cpp
new file mode 100644
@@ -0,0 +1,30 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+// SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+/* C++ reimplementation of the gpiodetect tool. */
+
+#include <cstdlib>
+#include <filesystem>
+#include <gpiod.hpp>
+#include <iostream>
+
+int main(int argc, char **argv)
+{
+ if (argc != 1) {
+ ::std::cerr << "usage: " << argv[0] << ::std::endl;
+ return EXIT_FAILURE;
+ }
+
+ for (const auto& entry: ::std::filesystem::directory_iterator("/dev/")) {
+ if (::gpiod::is_gpiochip_device(entry.path())) {
+ ::gpiod::chip chip(entry.path());
+ auto info = chip.get_info();
+
+ ::std::cout << info.name() << " [" <<
+ info.label() << "] (" <<
+ info.num_lines() << " lines)" << ::std::endl;
+ }
+ }
+
+ return EXIT_SUCCESS;
+}
new file mode 100644
@@ -0,0 +1,32 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+// SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+/* C++ reimplementation of the gpiofind tool. */
+
+#include <gpiod.hpp>
+
+#include <cstdlib>
+#include <filesystem>
+#include <iostream>
+
+int main(int argc, char **argv)
+{
+ if (argc != 2) {
+ ::std::cerr << "usage: " << argv[0] << " <line name>" << ::std::endl;
+ return EXIT_FAILURE;
+ }
+
+ for (const auto& entry: ::std::filesystem::directory_iterator("/dev/")) {
+ if (::gpiod::is_gpiochip_device(entry.path())) {
+ ::gpiod::chip chip(entry.path());
+
+ auto offset = chip.get_line_offset_from_name(argv[1]);
+ if (offset >= 0) {
+ ::std::cout << chip.get_info().name() << " " << offset << ::std::endl;
+ return EXIT_SUCCESS;
+ }
+ }
+ }
+
+ return EXIT_FAILURE;
+}
new file mode 100644
@@ -0,0 +1,38 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+// SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+/* Simplified C++ reimplementation of the gpioget tool. */
+
+#include <gpiod.hpp>
+
+#include <cstdlib>
+#include <iostream>
+
+int main(int argc, char **argv)
+{
+ if (argc < 3) {
+ ::std::cerr << "usage: " << argv[0] << " <chip> <line_offset0> ..." << ::std::endl;
+ return EXIT_FAILURE;
+ }
+
+ ::gpiod::line::offsets offsets;
+
+ for (int i = 2; i < argc; i++)
+ offsets.push_back(::std::stoul(argv[i]));
+
+ ::gpiod::chip chip(argv[1]);
+ auto request = chip.request_lines(
+ ::gpiod::request_config({
+ { ::gpiod::request_config::property::OFFSETS, offsets },
+ { ::gpiod::request_config::property::CONSUMER, "gpiogetcxx" }
+ }),
+ ::gpiod::line_config());
+
+ auto vals = request.get_values();
+
+ for (auto& it: vals)
+ ::std::cout << (it == ::gpiod::line::value::ACTIVE ? "1" : "0") << ' ';
+ ::std::cout << ::std::endl;
+
+ return EXIT_SUCCESS;
+}
new file mode 100644
@@ -0,0 +1,61 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+// SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+/* Simplified C++ reimplementation of the gpioinfo tool. */
+
+#include <gpiod.hpp>
+
+#include <cstdlib>
+#include <filesystem>
+#include <iostream>
+
+namespace {
+
+void show_chip(const ::gpiod::chip& chip)
+{
+ auto info = chip.get_info();
+
+ ::std::cout << info.name() << " - " << info.num_lines() << " lines:" << ::std::endl;
+
+ for (unsigned int offset = 0; offset < info.num_lines(); offset++) {
+ auto info = chip.get_line_info(offset);
+
+ ::std::cout << "\tline ";
+ ::std::cout.width(3);
+ ::std::cout << info.offset() << ": ";
+
+ ::std::cout.width(12);
+ ::std::cout << (info.name().empty() ? "unnamed" : info.name());
+ ::std::cout << " ";
+
+ ::std::cout.width(12);
+ ::std::cout << (info.consumer().empty() ? "unused" : info.consumer());
+ ::std::cout << " ";
+
+ ::std::cout.width(8);
+ ::std::cout << (info.direction() == ::gpiod::line::direction::INPUT ? "input" : "output");
+ ::std::cout << " ";
+
+ ::std::cout.width(10);
+ ::std::cout << (info.active_low() ? "active-low" : "active-high");
+
+ ::std::cout << ::std::endl;
+ }
+}
+
+} /* namespace */
+
+int main(int argc, char **argv)
+{
+ if (argc != 1) {
+ ::std::cerr << "usage: " << argv[0] << ::std::endl;
+ return EXIT_FAILURE;
+ }
+
+ for (const auto& entry: ::std::filesystem::directory_iterator("/dev/")) {
+ if (::gpiod::is_gpiochip_device(entry.path()))
+ show_chip(::gpiod::chip(entry.path()));
+ }
+
+ return EXIT_SUCCESS;
+}
new file mode 100644
@@ -0,0 +1,74 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+// SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+/* Simplified C++ reimplementation of the gpiomon tool. */
+
+#include <chrono>
+#include <cstdlib>
+#include <gpiod.hpp>
+#include <iostream>
+
+namespace {
+
+void print_event(const ::gpiod::edge_event& event)
+{
+ if (event.type() == ::gpiod::edge_event::event_type::RISING_EDGE)
+ ::std::cout << " RISING EDGE";
+ else
+ ::std::cout << "FALLING EDGE";
+
+ ::std::cout << " ";
+
+ ::std::cout << event.timestamp_ns() / 1000000000;
+ ::std::cout << ".";
+ ::std::cout << event.timestamp_ns() % 1000000000;
+
+ ::std::cout << " line: " << event.line_offset();
+
+ ::std::cout << ::std::endl;
+}
+
+} /* namespace */
+
+int main(int argc, char **argv)
+{
+ if (argc < 3) {
+ ::std::cout << "usage: " << argv[0] << " <chip> <offset0> ..." << ::std::endl;
+ return EXIT_FAILURE;
+ }
+
+ ::gpiod::line::offsets offsets;
+ offsets.reserve(argc);
+ for (int i = 2; i < argc; i++)
+ offsets.push_back(::std::stoul(argv[i]));
+
+ ::gpiod::chip chip(argv[1]);
+ auto request = chip.request_lines(
+ ::gpiod::request_config({
+ { ::gpiod::request_config::property::OFFSETS, offsets},
+ { ::gpiod::request_config::property::CONSUMER, "gpiomoncxx"},
+ }),
+ ::gpiod::line_config({
+ {
+ ::gpiod::line_config::property::DIRECTION,
+ ::gpiod::line::direction::INPUT
+ },
+ {
+ ::gpiod::line_config::property::EDGE,
+ ::gpiod::line::edge::BOTH
+ }
+ }));
+
+ ::gpiod::edge_event_buffer buffer;
+
+ for (;;) {
+ if (request.wait_edge_event(::std::chrono::seconds(5))) {
+ request.read_edge_event(buffer);
+
+ for (const auto& event: buffer)
+ print_event(event);
+ }
+ }
+
+ return EXIT_SUCCESS;
+}
new file mode 100644
@@ -0,0 +1,57 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+// SPDX-FileCopyrightText: 2017-2021 Bartosz Golaszewski <bartekgola@gmail.com>
+
+/* Simplified C++ reimplementation of the gpioset tool. */
+
+#include <gpiod.hpp>
+
+#include <cstdlib>
+#include <iostream>
+
+int main(int argc, char **argv)
+{
+ if (argc < 3) {
+ ::std::cerr << "usage: " << argv[0] <<
+ " <chip> <line_offset0>=<value0> ..." << ::std::endl;
+ return EXIT_FAILURE;
+ }
+
+ ::gpiod::line::offsets offsets;
+ ::gpiod::line::values values;
+
+ for (int i = 2; i < argc; i++) {
+ ::std::string arg(argv[i]);
+
+ size_t pos = arg.find('=');
+
+ ::std::string offset(arg.substr(0, pos));
+ ::std::string value(arg.substr(pos + 1, ::std::string::npos));
+
+ if (offset.empty() || value.empty())
+ throw ::std::invalid_argument("invalid offset=value mapping: " +
+ ::std::string(argv[i]));
+
+ offsets.push_back(::std::stoul(offset));
+ values.push_back(::std::stoul(value) ? ::gpiod::line::value::ACTIVE :
+ ::gpiod::line::value::INACTIVE);
+ }
+
+ ::gpiod::chip chip(argv[1]);
+ auto request = chip.request_lines(
+ ::gpiod::request_config({
+ { ::gpiod::request_config::property::OFFSETS, offsets },
+ { ::gpiod::request_config::property::CONSUMER, "gpiogetcxx" }
+ }),
+ ::gpiod::line_config({
+ {
+ ::gpiod::line_config::property::DIRECTION,
+ ::gpiod::line::direction::OUTPUT
+ }
+ }));
+
+ request.set_values(values);
+
+ ::std::cin.get();
+
+ return EXIT_SUCCESS;
+}
This adds a couple example tools written using the new bindings. Signed-off-by: Bartosz Golaszewski <brgl@bgdev.pl> --- bindings/cxx/examples/.gitignore | 9 +++ bindings/cxx/examples/Makefile.am | 26 +++++++++ bindings/cxx/examples/gpiodetectcxx.cpp | 30 ++++++++++ bindings/cxx/examples/gpiofindcxx.cpp | 32 +++++++++++ bindings/cxx/examples/gpiogetcxx.cpp | 38 +++++++++++++ bindings/cxx/examples/gpioinfocxx.cpp | 61 ++++++++++++++++++++ bindings/cxx/examples/gpiomoncxx.cpp | 74 +++++++++++++++++++++++++ bindings/cxx/examples/gpiosetcxx.cpp | 57 +++++++++++++++++++ 8 files changed, 327 insertions(+) create mode 100644 bindings/cxx/examples/.gitignore create mode 100644 bindings/cxx/examples/Makefile.am create mode 100644 bindings/cxx/examples/gpiodetectcxx.cpp create mode 100644 bindings/cxx/examples/gpiofindcxx.cpp create mode 100644 bindings/cxx/examples/gpiogetcxx.cpp create mode 100644 bindings/cxx/examples/gpioinfocxx.cpp create mode 100644 bindings/cxx/examples/gpiomoncxx.cpp create mode 100644 bindings/cxx/examples/gpiosetcxx.cpp