@@ -120,6 +120,8 @@ AS_IF([test "x$with_tools" = xtrue],
AC_CHECK_FUNC([asprintf], [], [FUNC_NOT_FOUND_TOOLS([asprintf])])
AC_CHECK_FUNC([scandir], [], [FUNC_NOT_FOUND_TOOLS([scandir])])
AC_CHECK_FUNC([versionsort], [], [FUNC_NOT_FOUND_TOOLS([versionsort])])
+ AC_CHECK_FUNC([strtoull], [], [FUNC_NOT_FOUND_TOOLS([strtoull])])
+ AC_CHECK_FUNC([nanosleep], [], [FUNC_NOT_FOUND_TOOLS([nanosleep])])
AS_IF([test "x$with_gpioset_interactive" = xtrue],
[PKG_CHECK_MODULES([LIBEDIT], [libedit >= 3.1])])
])
@@ -19,7 +19,7 @@ struct config {
bool unquoted;
enum gpiod_line_bias bias;
enum gpiod_line_direction direction;
- unsigned int hold_period_us;
+ unsigned long long hold_period_us;
const char *chip_id;
const char *consumer;
};
@@ -205,7 +205,7 @@ int main(int argc, char **argv)
die_perror("unable to request lines");
if (cfg.hold_period_us)
- usleep(cfg.hold_period_us);
+ sleep_us(cfg.hold_period_us);
ret = gpiod_line_request_get_values(request, values);
if (ret)
@@ -5,6 +5,7 @@
#include <getopt.h>
#include <gpiod.h>
#include <inttypes.h>
+#include <limits.h>
#include <poll.h>
#include <stdio.h>
#include <stdlib.h>
@@ -24,13 +25,13 @@ struct config {
enum gpiod_line_bias bias;
enum gpiod_line_edge edges;
int events_wanted;
- unsigned int debounce_period_us;
+ unsigned long long debounce_period_us;
const char *chip_id;
const char *consumer;
const char *fmt;
enum gpiod_line_clock event_clock;
int timestamp_fmt;
- int idle_timeout;
+ long long idle_timeout;
};
static void print_help(void)
@@ -390,9 +391,14 @@ int main(int argc, char **argv)
if (cfg.active_low)
gpiod_line_settings_set_active_low(settings, true);
- if (cfg.debounce_period_us)
+ if (cfg.debounce_period_us) {
+ if (cfg.debounce_period_us > UINT_MAX)
+ die("maximum debounce period is %uus, got %lluus",
+ UINT_MAX, cfg.debounce_period_us);
+
gpiod_line_settings_set_debounce_period_us(
- settings, cfg.debounce_period_us);
+ settings, (unsigned long)cfg.debounce_period_us);
+ }
gpiod_line_settings_set_event_clock(settings, cfg.event_clock);
gpiod_line_settings_set_edge_detection(settings, cfg.edges);
@@ -23,7 +23,7 @@ struct config {
const char *chip_id;
const char *fmt;
int timestamp_fmt;
- int idle_timeout;
+ long long idle_timeout;
};
static void print_help(void)
@@ -28,8 +28,8 @@ struct config {
enum gpiod_line_bias bias;
enum gpiod_line_drive drive;
int toggles;
- unsigned int *toggle_periods;
- unsigned int hold_period_us;
+ unsigned long long *toggle_periods;
+ unsigned long long hold_period_us;
const char *chip_id;
const char *consumer;
};
@@ -94,10 +94,10 @@ static int parse_drive_or_die(const char *option)
return 0;
}
-static int parse_periods_or_die(char *option, unsigned int **periods)
+static int parse_periods_or_die(char *option, unsigned long long **periods)
{
int i, num_periods = 1;
- unsigned int *pp;
+ unsigned long long *pp;
char *end;
for (i = 0; option[i] != '\0'; i++)
@@ -376,7 +376,7 @@ static void toggle_all_lines(struct line_resolver *resolver)
* and apply the values to the requests.
* offset and values are scratch pads for working.
*/
-static void toggle_sequence(int toggles, unsigned int *toggle_periods,
+static void toggle_sequence(int toggles, unsigned long long *toggle_periods,
struct gpiod_line_request **requests,
struct line_resolver *resolver,
unsigned int *offsets,
@@ -388,7 +388,7 @@ static void toggle_sequence(int toggles, unsigned int *toggle_periods,
return;
for (;;) {
- usleep(toggle_periods[i]);
+ sleep_us(toggle_periods[i]);
toggle_all_lines(resolver);
apply_values(requests, resolver, offsets, values);
@@ -826,7 +826,7 @@ static void interact(struct gpiod_line_request **requests,
printf("invalid period: '%s'\n", words[1]);
goto cmd_ok;
}
- usleep(period_us);
+ sleep_us(period_us);
goto cmd_ok;
}
@@ -981,7 +981,7 @@ int main(int argc, char **argv)
}
if (cfg.hold_period_us)
- usleep(cfg.hold_period_us);
+ sleep_us(cfg.hold_period_us);
#ifdef GPIOSET_INTERACTIVE
if (cfg.interactive)
@@ -112,12 +112,12 @@ int parse_bias_or_die(const char *option)
return GPIOD_LINE_BIAS_DISABLED;
}
-int parse_period(const char *option)
+long long parse_period(const char *option)
{
- unsigned long p, m = 0;
+ unsigned long long p, m = 0;
char *end;
- p = strtoul(option, &end, 10);
+ p = strtoull(option, &end, 10);
switch (*end) {
case 'u':
@@ -147,15 +147,15 @@ int parse_period(const char *option)
}
p *= m;
- if (*end != '\0' || p > INT_MAX)
+ if (*end != '\0' || p > LLONG_MAX)
return -1;
return p;
}
-unsigned int parse_period_or_die(const char *option)
+unsigned long long parse_period_or_die(const char *option)
{
- int period = parse_period(option);
+ long long period = parse_period(option);
if (period < 0)
die("invalid period: %s", option);
@@ -163,6 +163,16 @@ unsigned int parse_period_or_die(const char *option)
return period;
}
+void sleep_us(unsigned long long period)
+{
+ struct timespec spec;
+
+ spec.tv_sec = period / 1000000;
+ spec.tv_nsec = (period % 1000000) * 1000;
+
+ nanosleep(&spec, NULL);
+}
+
int parse_uint(const char *option)
{
unsigned long o;
@@ -87,8 +87,9 @@ void die(const char *fmt, ...) NORETURN PRINTF(1, 2);
void die_perror(const char *fmt, ...) NORETURN PRINTF(1, 2);
void print_version(void);
int parse_bias_or_die(const char *option);
-int parse_period(const char *option);
-unsigned int parse_period_or_die(const char *option);
+long long parse_period(const char *option);
+unsigned long long parse_period_or_die(const char *option);
+void sleep_us(unsigned long long period);
int parse_uint(const char *option);
unsigned int parse_uint_or_die(const char *option);
void print_bias_help(void);