blind

suckless command-line video editing utility
git clone git://git.suckless.org/blind
Log | Files | Refs | README | LICENSE

commit a2dfbb3368ce0e998f774dd294383772651d1302
parent 4674ec0e4b833ab0d0365225ba99228df14abe87
Author: Mattias Andrée <maandree@kth.se>
Date:   Sat, 14 Jan 2017 04:40:03 +0100

Fix errors, blind-{to,from}-{video,image} works

Signed-off-by: Mattias Andrée <maandree@kth.se>

Diffstat:
Msrc/blind-concat.c | 2+-
Msrc/blind-from-image.c | 17+++++++++++------
Msrc/blind-from-text.c | 8++++----
Msrc/blind-from-video.c | 89++++++++++++++++++++++++++++++++-----------------------------------------------
Msrc/blind-gauss-blur.c | 5+++--
Msrc/blind-next-frame.c | 2+-
Msrc/blind-rewrite-head.c | 12++++++------
Msrc/blind-to-image.c | 14+++++++-------
Msrc/blind-to-video.c | 44+++++++++++++++++++++-----------------------
Msrc/stream.c | 12++++++------
Msrc/util.c | 1-
Msrc/util.h | 1+
Asrc/util/endian.h | 43+++++++++++++++++++++++++++++++++++++++++++
Msrc/util/to.h | 8++++----
14 files changed, 144 insertions(+), 114 deletions(-)

diff --git a/src/blind-concat.c b/src/blind-concat.c @@ -79,7 +79,7 @@ concat_to_file(int argc, char *argv[], char *output_file) ewriteall(fd, head, (size_t)headlen, output_file); - data = mmap(0, size + (size_t)headlen, PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0); + data = mmap(0, size + (size_t)headlen, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (data == MAP_FAILED) eprintf("mmap %s:", output_file); memmove(data + headlen, data, size); diff --git a/src/blind-from-image.c b/src/blind-from-image.c @@ -97,10 +97,16 @@ static size_t pam_head(int fd, const char *fname) { size_t ptr; + ssize_t r; char *p; unsigned long long int maxval = UINT8_MAX; for (ptr = 0;;) { - ptr += ereadall(fd, buf + ptr, (size_t)buf - ptr, fname); + r = read(fd, buf + ptr, sizeof(buf) - 1); + if (r < 0) + eprintf("read %s:", fname); + if (r == 0) + eprintf("%s\n", conv_fail_msg); + ptr += (size_t)r; for (;;) { p = memchr(buf, '\n', ptr); if (!p) { @@ -148,13 +154,13 @@ pam_head(int fd, const char *fname) } } header_done: - if (maxval < (size_t)UINT8_MAX) { + if (maxval <= (size_t)UINT8_MAX) { pixel_size = sizeof(uint8_t); get_value = get_value_u8; - } else if (maxval < (size_t)UINT16_MAX) { + } else if (maxval <= (size_t)UINT16_MAX) { pixel_size = sizeof(uint16_t); get_value = get_value_u16; - } else if (maxval < (size_t)UINT32_MAX) { + } else if (maxval <= (size_t)UINT32_MAX) { pixel_size = sizeof(uint32_t); get_value = get_value_u32; } else { @@ -176,7 +182,6 @@ main(int argc, char *argv[]) size_t off, n; ssize_t r; const char *file = "<subprocess>"; - const char *conv_fail_msg = "convertion failed, if converting a farbfeld file, try -f"; ARGBEGIN { case 'f': @@ -202,7 +207,7 @@ main(int argc, char *argv[]) else forked = 1; - if (forked) { + if (!forked) { file = "<stdin>"; pipe_rw[0] = STDIN_FILENO; goto after_fork; diff --git a/src/blind-from-text.c b/src/blind-from-text.c @@ -10,7 +10,7 @@ USAGE("") static void -process_xyza(struct stream *stream) +process_xyza(void) { double buf[BUFSIZ / sizeof(double)]; size_t i; @@ -35,7 +35,7 @@ main(int argc, char *argv[]) size_t size = 0; char *line = NULL; ssize_t len; - void (*process)(struct stream *stream) = NULL; + void (*process)(void) = NULL; ENOFLAGS(argc); @@ -48,7 +48,7 @@ main(int argc, char *argv[]) } if (len && line[len - 1] == '\n') line[--len] = '\n'; - if (len + 6 > sizeof(stream.buf)) + if ((size_t)len + 6 > sizeof(stream.buf)) eprintf("<stdin>: head is too long\n"); stream.fd = -1; stream.file = "<stdin>"; @@ -64,7 +64,7 @@ main(int argc, char *argv[]) else eprintf("pixel format %s is not supported, try xyza\n", stream.pixfmt); - process(&stream); + process(); efshut(stdin, "<stdin>"); return 0; diff --git a/src/blind-from-video.c b/src/blind-from-video.c @@ -2,7 +2,6 @@ #include "stream.h" #include "util.h" -#include <arpa/inet.h> #if defined(HAVE_PRCTL) # include <sys/prctl.h> #endif @@ -20,30 +19,23 @@ USAGE("[-r frame-rate] [-w width -h height] [-d] input-file output-file") static int draft = 0; static void -read_metadata(FILE *fp, char *fname, size_t *width, size_t *height, size_t *frames) +read_metadata(FILE *fp, char *fname, size_t *width, size_t *height) { char *line = NULL; size_t size = 0; ssize_t len; - int have_width = !width, have_height = !height, have_frames = 0; char *p; while ((len = getline(&line, &size, fp)) != -1) { if (len && line[len - 1]) line[--len] = '\0'; p = strchr(line, '=') + 1; - if (width && strstr(line, "width=") == line) { + if (strstr(line, "width=") == line) { if (tozu(p, 1, SIZE_MAX, width)) eprintf("invalid width: %s\n", p); - have_width = 1; - } else if (height && strstr(line, "height=") == line) { + } else if (strstr(line, "height=") == line) { if (tozu(p, 1, SIZE_MAX, height)) eprintf("invalid height: %s\n", p); - have_height = 1; - } else if (strstr(line, "nb_read_frames=") == line) { - if (tozu(p, 0, SIZE_MAX, frames)) - eprintf("invalid frame count: %s\n", p); - have_frames = 1; } } @@ -51,12 +43,12 @@ read_metadata(FILE *fp, char *fname, size_t *width, size_t *height, size_t *fram eprintf("getline %s:", fname); free(line); - if (have_width + have_height + have_frames < 3) + if (!*width || !*height) eprintf("could not get all required metadata\n"); } static void -get_metadata(char *file, size_t *width, size_t *height, size_t *frames) +get_metadata(char *file, size_t *width, size_t *height) { FILE *fp; int fd, pipe_rw[2]; @@ -83,7 +75,7 @@ get_metadata(char *file, size_t *width, size_t *height, size_t *frames) eprintf("dup2:"); close(pipe_rw[1]); execlp("ffprobe", "ffprobe", "-v", "quiet", "-show_streams", - "-select_streams", "v", "-count_frames", "-", NULL); + "-select_streams", "v", "-", NULL); eprintf("exec ffprobe:"); } @@ -91,7 +83,7 @@ get_metadata(char *file, size_t *width, size_t *height, size_t *frames) fp = fdopen(pipe_rw[0], "rb"); if (!fp) eprintf("fdopen <subprocess>:"); - read_metadata(fp, file, width, height, frames); + read_metadata(fp, file, width, height); fclose(fp); close(pipe_rw[0]); @@ -111,10 +103,10 @@ convert_segment(char *buf, size_t n, int fd, char *file) pixel_t pixels[1024]; if (draft) { for (ptr = i = 0; ptr < n; ptr += 8) { - pixels[i][3] = ntohs(((uint16_t *)(buf + ptr))[0]) / max; - y = (ntohs(((uint16_t *)(buf + ptr))[1]) - 16 * 256); - u = (ntohs(((uint16_t *)(buf + ptr))[2]) - 128 * 256); - v = (ntohs(((uint16_t *)(buf + ptr))[3]) - 128 * 256); + pixels[i][3] = 1; + y = (long int)(le16toh(((uint16_t *)(buf + ptr))[1])) - 16L * 256L; + u = (long int)(le16toh(((uint16_t *)(buf + ptr))[2])) - 128L * 256L; + v = (long int)(le16toh(((uint16_t *)(buf + ptr))[3])) - 128L * 256L; scaled_yuv_to_ciexyz(y, u, v, pixels[i] + 0, pixels[i] + 1, pixels[i] + 2); if (++i == 1024) { i = 0; @@ -123,10 +115,10 @@ convert_segment(char *buf, size_t n, int fd, char *file) } } else { for (ptr = i = 0; ptr < n; ptr += 8) { - pixels[i][3] = ntohs(((uint16_t *)(buf + ptr))[0]) / max; - y = (ntohs(((uint16_t *)(buf + ptr))[1]) - 16 * 256) / max; - u = (ntohs(((uint16_t *)(buf + ptr))[2]) - 128 * 256) / max; - v = (ntohs(((uint16_t *)(buf + ptr))[3]) - 128 * 256) / max; + pixels[i][3] = le16toh(((uint16_t *)(buf + ptr))[0]) / max; + y = ((long int)le16toh(((uint16_t *)(buf + ptr))[1]) - 16L * 256L) / max; + u = ((long int)le16toh(((uint16_t *)(buf + ptr))[2]) - 128L * 256L) / max; + v = ((long int)le16toh(((uint16_t *)(buf + ptr))[3]) - 128L * 256L) / max; yuv_to_srgb(y, u, v, &r, &g, &b); r = srgb_decode(r); g = srgb_decode(g); @@ -145,14 +137,15 @@ convert_segment(char *buf, size_t n, int fd, char *file) static void convert(char *infile, int outfd, char *outfile, size_t width, size_t height, char *frame_rate) { - char geometry[2 * 3 * sizeof(size_t) + 2], *cmd[13], buf[BUFSIZ]; - int status, fd, pipe_rw[2]; + char geometry[2 * 3 * sizeof(size_t) + 2], buf[BUFSIZ]; + const char *cmd[13]; + int status, pipe_rw[2]; size_t i = 0, n, ptr; ssize_t r; pid_t pid; cmd[i++] = "ffmpeg"; - cmd[i++] = "-i", cmd[i++] = "-"; + cmd[i++] = "-i", cmd[i++] = infile; cmd[i++] = "-f", cmd[i++] = "rawvideo"; cmd[i++] = "-pix_fmt", cmd[i++] = "ayuv64le"; if (width && height) { @@ -175,10 +168,6 @@ convert(char *infile, int outfd, char *outfile, size_t width, size_t height, cha #if defined(HAVE_PRCTL) && defined(PR_SET_PDEATHSIG) prctl(PR_SET_PDEATHSIG, SIGKILL); #endif - fd = eopen(infile, O_RDONLY); - if (dup2(fd, STDIN_FILENO) == -1) - eprintf("dup2:"); - close(fd); close(pipe_rw[0]); if (dup2(pipe_rw[1], STDOUT_FILENO) == -1) eprintf("dup2:"); @@ -220,9 +209,8 @@ main(int argc, char *argv[]) char *outfile; char *data; ssize_t headlen; - size_t length; - int outfd, status; - pid_t pid; + size_t length, frame_size; + int outfd; struct stat st; ARGBEGIN { @@ -248,34 +236,29 @@ main(int argc, char *argv[]) infile = argv[0]; outfile = argv[1]; - outfd = eopen(outfile, O_RDWR | O_CREAT | O_TRUNC, 0666); - - pid = fork(); - if (pid == -1) - eprintf("fork:"); - - if (!pid) { -#if defined(HAVE_PRCTL) && defined(PR_SET_PDEATHSIG) - prctl(PR_SET_PDEATHSIG, SIGKILL); -#endif - convert(infile, outfd, outfile, width, height, frame_rate); - exit(0); - } - - get_metadata(infile, width ? NULL : &width, height ? NULL : &height, &frames); + if (!width) + get_metadata(infile, &width, &height); + if (width > SIZE_MAX / height) + eprintf("video frame too large\n"); + frame_size = width * height; + if (4 * sizeof(double) > SIZE_MAX / frame_size) + eprintf("video frame too large\n"); + frame_size *= 4 * sizeof(double); - if (waitpid(pid, &status, 0) == -1) - eprintf("waitpid:"); - if (status) - exit(1); + outfd = eopen(outfile, O_RDWR | O_CREAT | O_TRUNC, 0666); + convert(infile, outfd, outfile, width, height, frame_rate); if (fstat(outfd, &st)) eprintf("fstat %s:", outfile); length = (size_t)(st.st_size); + if (length % frame_size) + eprintf("<subprocess>: incomplete frame"); + frames = length / frame_size; + sprintf(head, "%zu %zu %zu %s\n%cuivf%zn", frames, width, height, "xyza", 0, &headlen); ewriteall(outfd, head, (size_t)headlen, outfile); - data = mmap(0, length + (size_t)headlen, PROT_READ | PROT_WRITE, MAP_PRIVATE, outfd, 0); + data = mmap(0, length + (size_t)headlen, PROT_READ | PROT_WRITE, MAP_SHARED, outfd, 0); memmove(data + headlen, data, length); memcpy(data, head, (size_t)headlen); munmap(data, length + (size_t)headlen); diff --git a/src/blind-gauss-blur.c b/src/blind-gauss-blur.c @@ -17,7 +17,7 @@ static size_t jobs = 1; static void process_xyza(char *restrict output, char *restrict cbuf, char *restrict sbuf, - struct stream *colour, struct stream *sigma, size_t n, size_t unused) + struct stream *colour, struct stream *sigma, size_t n, size_t sn) { typedef double pixel_t[4]; @@ -141,7 +141,8 @@ process_xyza(char *restrict output, char *restrict cbuf, char *restrict sbuf, } } - (void) unused; + (void) sigma; + (void) sn; } int diff --git a/src/blind-next-frame.c b/src/blind-next-frame.c @@ -56,7 +56,7 @@ main(int argc, char *argv[]) } done: - if (stream.height || n) + if (anything && (stream.height || n)) enprintf(2, "incomplete frame\n"); return !anything; diff --git a/src/blind-rewrite-head.c b/src/blind-rewrite-head.c @@ -42,22 +42,22 @@ rewrite(struct stream *stream, int frames_auto) stream->frames, stream->width, stream->height, stream->pixfmt, 0, &headlen); length = stream->frames * frame_size; - if (length > (size_t)SSIZE_MAX || headlen > (size_t)SSIZE_MAX - length) + if (length > (size_t)SSIZE_MAX || (size_t)headlen > (size_t)SSIZE_MAX - length) eprintf("%s: video is too long\n", stream->file); - if (headlen > stream->headlen) + if ((size_t)headlen > stream->headlen) if (ftruncate(stream->fd, length + headlen)) eprintf("ftruncate %s:", stream->file); - data = mmap(0, length + (size_t)headlen, PROT_READ | PROT_WRITE, MAP_PRIVATE, stream->fd, 0); + data = mmap(0, length + (size_t)headlen, PROT_READ | PROT_WRITE, MAP_SHARED, stream->fd, 0); if (data == MAP_FAILED) eprintf("mmap %s:", stream->file); - if (headlen != stream->headlen) + if ((size_t)headlen != stream->headlen) memmove(data + headlen, data + stream->headlen, length); memcpy(data, head, (size_t)headlen); munmap(data, length + (size_t)headlen); - if (headlen < stream->headlen) + if ((size_t)headlen < stream->headlen) if (ftruncate(stream->fd, length + headlen)) eprintf("ftruncate %s:", stream->file); } @@ -80,7 +80,7 @@ main(int argc, char *argv[]) if (headless) { if (argc != 5) eprintf("all positional arguments are mandatory unless -h is used\n"); - } else if (argc != 1 || argc != 2 || argc != 4 || argc != 5) { + } else if (argc != 1 && argc != 2 && argc != 4 && argc != 5) { usage(); } diff --git a/src/blind-to-image.c b/src/blind-to-image.c @@ -46,14 +46,14 @@ write_pixel(double R, double G, double B, double A, int bytes, unsigned long lon colours[2] = srgb_encode(B) * max + 0.5; colours[3] = A * max + 0.5; - for (i = k = 0; i < 4; i++) { - for (j = 0; j < bytes; j++, k++) { - buf[k + bm - j] = (unsigned char)(colours[j]); - colours[j] >>= 8; + for (i = k = 0; i < 4; i++, k += bytes) { + for (j = 0; j < bytes; j++) { + buf[k + bm - j] = (unsigned char)(colours[i]); + colours[i] >>= 8; } } - ewriteall(STDOUT_FILENO, buf, (size_t)bytes * 4, "<stdout>"); + ewriteall(STDOUT_FILENO, buf, k, "<stdout>"); } static void @@ -75,7 +75,7 @@ process_xyza(struct stream *stream, size_t n, int bytes, unsigned long long int } } - srgb_to_ciexyz(X, Y, Z, &R, &G, &B); + ciexyz_to_srgb(X, Y, Z, &R, &G, &B); write_pixel(R, G, B, A, bytes, max); } } @@ -109,7 +109,7 @@ main(int argc, char *argv[]) max = 1ULL << (depth - 1); max |= max - 1; - for (bytes = 1; bytes * 8 < depth; bytes++); + bytes = (depth + 7) / 8; if (!strcmp(stream.pixfmt, "xyza")) process = process_xyza; diff --git a/src/blind-to-video.c b/src/blind-to-video.c @@ -2,7 +2,6 @@ #include "stream.h" #include "util.h" -#include <arpa/inet.h> #if defined(HAVE_PRCTL) # include <sys/prctl.h> #endif @@ -28,22 +27,21 @@ process_xyza(char *buf, size_t n, int fd, const char *fname) pixels = pixbuf; end = pixbuf + ELEMENTSOF(pixbuf); if (draft) { - for (ptr = 0; ptr < n; ptr += sizeof(pixel)) { + for (ptr = 0; ptr < n; ptr += 4 * sizeof(double)) { pixel = (double *)(buf + ptr); - a = (long int)(pixel[3] * 0xFFFFL); ciexyz_to_scaled_yuv(pixel[0], pixel[1], pixel[2], &r, &g, &b); - y = (long int)r + 16 * 256; - u = (long int)g + 128 * 256; - v = (long int)b + 128 * 256; - *pixels++ = htons((uint16_t)(a < 0 ? 0 : a > 0xFFFFL ? 0xFFFFL : a)); - *pixels++ = htons((uint16_t)(y < 0 ? 0 : y > 0xFFFFL ? 0xFFFFL : y)); - *pixels++ = htons((uint16_t)(u < 0 ? 0 : u > 0xFFFFL ? 0xFFFFL : u)); - *pixels++ = htons((uint16_t)(v < 0 ? 0 : v > 0xFFFFL ? 0xFFFFL : v)); + y = (long int)r + 16L * 256L; + u = (long int)g + 128L * 256L; + v = (long int)b + 128L * 256L; + *pixels++ = 0xFFFFU; + *pixels++ = htole16((uint16_t)(y < 0 ? 0 : y > 0xFFFFL ? 0xFFFFL : y)); + *pixels++ = htole16((uint16_t)(u < 0 ? 0 : u > 0xFFFFL ? 0xFFFFL : u)); + *pixels++ = htole16((uint16_t)(v < 0 ? 0 : v > 0xFFFFL ? 0xFFFFL : v)); if (pixels == end) ewriteall(fd, pixels = pixbuf, sizeof(pixbuf), fname); } } else { - for (ptr = 0; ptr < n; ptr += sizeof(pixel)) { + for (ptr = 0; ptr < n; ptr += 4 * sizeof(double)) { pixel = (double *)(buf + ptr); a = (long int)(pixel[3] * 0xFFFFL); ciexyz_to_srgb(pixel[0], pixel[1], pixel[2], &r, &g, &b); @@ -51,22 +49,19 @@ process_xyza(char *buf, size_t n, int fd, const char *fname) g = srgb_encode(g); b = srgb_encode(b); srgb_to_yuv(r, g, b, pixel + 0, pixel + 1, pixel + 2); - y = (long int)(pixel[0] * 0xFFFFL); - u = (long int)(pixel[1] * 0xFFFFL); - v = (long int)(pixel[2] * 0xFFFFL); - y += 16 * 256; - u += 128 * 256; - v += 128 * 256; - *pixels++ = htons((uint16_t)(a < 0 ? 0 : a > 0xFFFFL ? 0xFFFFL : a)); - *pixels++ = htons((uint16_t)(y < 0 ? 0 : y > 0xFFFFL ? 0xFFFFL : y)); - *pixels++ = htons((uint16_t)(u < 0 ? 0 : u > 0xFFFFL ? 0xFFFFL : u)); - *pixels++ = htons((uint16_t)(v < 0 ? 0 : v > 0xFFFFL ? 0xFFFFL : v)); + y = (long int)(pixel[0] * 0xFFFFL) + 16L * 256L; + u = (long int)(pixel[1] * 0xFFFFL) + 128L * 256L; + v = (long int)(pixel[2] * 0xFFFFL) + 128L * 256L; + *pixels++ = htole16((uint16_t)(a < 0 ? 0 : a > 0xFFFFL ? 0xFFFFL : a)); + *pixels++ = htole16((uint16_t)(y < 0 ? 0 : y > 0xFFFFL ? 0xFFFFL : y)); + *pixels++ = htole16((uint16_t)(u < 0 ? 0 : u > 0xFFFFL ? 0xFFFFL : u)); + *pixels++ = htole16((uint16_t)(v < 0 ? 0 : v > 0xFFFFL ? 0xFFFFL : v)); if (pixels == end) ewriteall(fd, pixels = pixbuf, sizeof(pixbuf), fname); } } if (pixels != pixbuf) - ewriteall(fd, pixels = pixbuf, sizeof(pixbuf), fname); + ewriteall(fd, pixbuf, (size_t)(pixels - pixbuf) * sizeof(*pixels), fname); } int @@ -128,11 +123,14 @@ main(int argc, char *argv[]) if (dup2(pipe_rw[0], STDIN_FILENO) == -1) eprintf("dup2:"); close(pipe_rw[0]); + execvp("ffmpeg", cmd); eprintf("exec ffmpeg:"); } + free(cmd); + close(pipe_rw[0]); - while (!eread_stream(&stream, SIZE_MAX)) { + while (eread_stream(&stream, SIZE_MAX)) { n = stream.ptr - (stream.ptr % stream.pixel_size); process(stream.buf, n, pipe_rw[1], "<subprocess>"); memmove(stream.buf, stream.buf + n, stream.ptr -= n); diff --git a/src/stream.c b/src/stream.c @@ -17,7 +17,7 @@ eninit_stream(int status, struct stream *stream) size_t n; char *p = NULL, *w, *h, *f, *end; - for (stream->ptr = 0; stream->fd >= 0 && p;) { + for (stream->ptr = 0; stream->fd >= 0 && !p;) { r = read(stream->fd, stream->buf + stream->ptr, sizeof(stream->buf) - stream->ptr); if (r < 0) enprintf(status, "read %s:", stream->file); @@ -87,7 +87,7 @@ eninit_stream(int status, struct stream *stream) return; bad_format: - enprintf(status, "%s: file format not supported%s\n", stream->file); + enprintf(status, "%s: file format not supported\n", stream->file); } @@ -167,9 +167,9 @@ void encheck_compat(int status, const struct stream *a, const struct stream *b) { if (a->width != b->width || a->height != b->height) - eprintf("videos do not have the same geometry\n"); + enprintf(status, "videos do not have the same geometry\n"); if (strcmp(a->pixfmt, b->pixfmt)) - eprintf("videos use incompatible pixel formats\n"); + enprintf(status, "videos use incompatible pixel formats\n"); } @@ -181,11 +181,11 @@ enread_frame(int status, struct stream *stream, void *buf, size_t n) for (; stream->ptr < n; stream->ptr += (size_t)r) { r = read(stream->fd, buffer + stream->ptr, n - stream->ptr); if (r < 0) { - eprintf("read %s:", stream->file); + enprintf(status, "read %s:", stream->file); } else if (r == 0) { if (!stream->ptr) break; - eprintf("%s: incomplete frame", stream->file); + enprintf(status, "%s: incomplete frame", stream->file); } } if (!stream->ptr) diff --git a/src/util.c b/src/util.c @@ -171,7 +171,6 @@ enfork_jobs(int status, size_t *start, size_t *end, size_t jobs) return 1; } - void enjoin_jobs(int status, int is_master) { diff --git a/src/util.h b/src/util.h @@ -16,3 +16,4 @@ #include "util/colour.h" #include "util/io.h" #include "util/jobs.h" +#include "util/endian.h" diff --git a/src/util/endian.h b/src/util/endian.h @@ -0,0 +1,43 @@ +/* See LICENSE file for copyright and license details. */ +#include <stdint.h> + +#if defined(HAVE_ENDIAN_H) +# include <endian.h> +#elif defined(HAVE_SYS_ENDIAN_H) +# include <sys/endian.h> +#endif + +#if !defined(HAVE_ENDIAN_H) && !defined(HAVE_SYS_ENDIAN_H) + +# if !defined(htole16) +# define htole16 blind_htole16 +static inline uint16_t +blind_htole16(uint16_t h) +{ + union { + unsigned char bytes[2]; + uint16_t value; + } d; + d.bytes[0] = h; + d.bytes[1] = h >> 8; + return d.value; +} +# endif + +# if !defined(le16toh) +# if defined(letoh16) +# define le16toh letoh16 +# else +# define le16toh blind_le16toh +static inline uint16_t +blind_le16toh(uint16_t le) +{ + unsigned char *bytes = (unsigned char *)&le; + return ((uint16_t)(bytes[1]) << 8) | (uint16_t)(bytes[0]); +} +# endif +# endif + +#elif defined(HAVE_OPENBSD_ENDIAN) +# define le16toh letoh16 +#endif diff --git a/src/util/to.h b/src/util/to.h @@ -29,7 +29,7 @@ DEF_STR_TO_INT(toi, int, tolli, long long int, "i") en##FNAME##_flag(int status, int flag, const char *s, TYPE min, TYPE max)\ {\ TYPE ret = 0;\ - if (!FNAME(s, min, max, &ret))\ + if (FNAME(s, min, max, &ret))\ enprintf(status,\ "argument of -%c must be an integer in [%"PRI", %"PRI"]\n",\ flag, min, max);\ @@ -46,7 +46,7 @@ DEF_STR_TO_INT(toi, int, tolli, long long int, "i") en##FNAME##_arg(int status, const char *name, const char *s, TYPE min, TYPE max)\ {\ TYPE ret = 0;\ - if (!FNAME(s, min, max, &ret))\ + if (FNAME(s, min, max, &ret))\ enprintf(status,\ "%s must be an integer in [%"PRI", %"PRI"]\n",\ name, min, max);\ @@ -104,7 +104,7 @@ DEF_STR_TO_INT(toi, int, "i") en##FNAME##_flag(int status, int flag, const char *s)\ {\ TYPE ret = 0;\ - if (!FNAME(s, &ret))\ + if (FNAME(s, &ret))\ enprintf(status, "argument of -%c must be floating-point value\n", flag);\ return ret;\ }\ @@ -119,7 +119,7 @@ DEF_STR_TO_INT(toi, int, "i") en##FNAME##_arg(int status, const char *name, const char *s)\ {\ TYPE ret = 0;\ - if (!FNAME(s, &ret))\ + if (FNAME(s, &ret))\ enprintf(status, "%s must be floating-point value\n", name);\ return ret;\ }\