2828#include < sys/types.h>
2929#include < unistd.h>
3030
31+ #include < algorithm>
3132#include < sstream>
3233#include < string>
3334#include < vector>
@@ -43,6 +44,7 @@ namespace gpio {
4344const char GPIODriver::GPIO_BASE_DIR[] = " /sys/class/gpio/gpio" ;
4445
4546using ola::thread::MutexLocker;
47+ using std::find;
4648using std::string;
4749using std::vector;
4850
@@ -122,7 +124,9 @@ bool GPIODriver::SetupGPIO() {
122124 * echo N > /sys/class/gpio/export
123125 * That requires root access.
124126 */
125- const string direction (" out" );
127+ const string normal_direction (" low" );
128+ const string inverted_direction (" high" );
129+ const string* direction = nullptr ;
126130 bool failed = false ;
127131 vector<uint16_t >::const_iterator iter = m_options.gpio_pins .begin ();
128132 for (; iter != m_options.gpio_pins .end (); ++iter) {
@@ -134,7 +138,12 @@ bool GPIODriver::SetupGPIO() {
134138 break ;
135139 }
136140
137- GPIOPin pin = {pin_fd, UNDEFINED, false };
141+ // Check if pin is in the inverted pin list
142+ bool inverted = (find (m_options.gpio_inverted_pins .begin (),
143+ m_options.gpio_inverted_pins .end (),
144+ (*iter)) != m_options.gpio_inverted_pins .end ());
145+
146+ GPIOPin pin = {pin_fd, UNDEFINED, false , inverted};
138147
139148 // Set dir
140149 str.str (" " );
@@ -144,9 +153,19 @@ bool GPIODriver::SetupGPIO() {
144153 failed = true ;
145154 break ;
146155 }
147- if (write (fd, direction.c_str (), direction.size ()) < 0 ) {
148- OLA_WARN << " Failed to enable output on " << str.str () << " : "
149- << strerror (errno);
156+ // Assign correct initial state
157+ if (inverted) {
158+ direction = &inverted_direction;
159+ } else {
160+ direction = &normal_direction;
161+ }
162+
163+ OLA_DEBUG << " Configuring GPIO pin " << static_cast <int >(*iter)
164+ << " with " << ( inverted ? " inverted" : " normal" ) << " logic" ;
165+ if (write (fd, direction->c_str (), direction->size ()) < 0 ) {
166+ OLA_WARN << " Failed to enable output on " << str.str ()
167+ << " with " << ( inverted ? " inverted" : " normal" ) << " logic"
168+ << " : " << strerror (errno);
150169 failed = true ;
151170 }
152171 close (fd);
@@ -191,7 +210,14 @@ bool GPIODriver::UpdateGPIOPins(const DmxBuffer &dmx) {
191210
192211 // Change the pin state if required.
193212 if (action != NO_CHANGE) {
194- char data = (action == TURN_ON ? ' 1' : ' 0' );
213+ char data;
214+ bool state = (action == TURN_ON);
215+ // Handle inverted logic appropriately
216+ if (m_gpio_pins[i].inverted ) {
217+ state = !state;
218+ }
219+ // Convert to char and write to sysfs
220+ data = (state ? ' 0' : ' 1' );
195221 if (write (m_gpio_pins[i].fd , &data, sizeof (data)) < 0 ) {
196222 OLA_WARN << " Failed to toggle GPIO pin " << i << " , fd "
197223 << static_cast <int >(m_gpio_pins[i].fd ) << " : "
0 commit comments