Skip to content

Commit

Permalink
Merge pull request #49 from teeuwen/master
Browse files Browse the repository at this point in the history
fix safe_fifo ENXIO; add safe_fifo error checking
  • Loading branch information
dpayne authored Oct 8, 2018
2 parents 334359f + dc6f21e commit e6d2fb4
Showing 1 changed file with 38 additions and 46 deletions.
84 changes: 38 additions & 46 deletions bin/safe_fifo.c
Original file line number Diff line number Diff line change
@@ -1,79 +1,71 @@
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <time.h>

#define BUF_SIZE 16384

char write_buffer[BUF_SIZE];
char read_buffer[BUF_SIZE];
char default_fifo_name[] = "/tmp/audio";

static struct timespec k_read_attempt_sleep_timespec = {0, 1L * 1000000L};

int main(int argc, char *argv[])
{
char *fifo_file_name;
char buf[BUF_SIZE];
struct stat st;
int fdr = 0, fdw = 0, n;

if (argc < 2)
{
fifo_file_name = default_fifo_name;
fifo_file_name = "/tmp/audio";
}
else
{
fifo_file_name = argv[1];
}

int retval = mkfifo(fifo_file_name, 777);
if (retval < 0)
if (mkfifo(fifo_file_name, 0666) < 0 && errno != EEXIST)
{
fprintf(stderr, "error creating fifo buffer: %d", errno);
return -1;
fprintf(stderr, "error creating fifo buffer: %d\n", errno);
goto err;
}

int fd = open(fifo_file_name, O_WRONLY | O_NONBLOCK, 0);

if (fd < 0)
// hacky solution to prevent ENXIO
if ((fdr = open(fifo_file_name, O_RDONLY | O_NONBLOCK, 0)) < 0)
{
fprintf(stderr, "error opening fifo buffer: %d", errno);
return -1;
fprintf(stderr, "error opening fifo buffer read only: %d\n", errno);
goto err;
}

// mark stdin as binary
freopen(NULL, "rb", stdin);
if ((fdw = open(fifo_file_name, O_WRONLY | O_NONBLOCK, 0)) < 0)
{
fprintf(stderr, "error opening fifo buffer write only: %d\n", errno);
goto err;
}

while (!feof(stdin))
if (fstat(fdw, &st) < 0)
{
// read input into buffer
int bytes_read = read(STDIN_FILENO, write_buffer, BUF_SIZE);
if (bytes_read > 0)
{
// pipe buffer to fifo
write(fd, write_buffer, bytes_read);
fprintf(stderr, "error running fstat on fifo buffer: %d\n", errno);
goto err;
}

// EAGAIN means the buffer is full, clear it and try again
if (errno == EAGAIN)
{
bytes_read = read(fd, read_buffer, BUF_SIZE);
if (bytes_read < 0)
{
fprintf(stderr, "error flushing fifo buffer: %d", errno);
}
}
}
else
{
break;
}
if (!S_ISFIFO(st.st_mode))
{
fprintf(stderr, "%s is no a fifo buffer\n", fifo_file_name);
goto err;
}

if (close(fd) < 0)
while (!feof(stdin) && (n = read(STDIN_FILENO, buf, BUF_SIZE)) > 0)
{
fprintf(stderr, "error closing fifo buffer: %d", errno);
return -1;
write(fdw, buf, n);
}
exit(0);

close(fdr);
close(fdw);

return 0;

err:
close(fdr);
close(fdw);

return 1;
}

0 comments on commit e6d2fb4

Please sign in to comment.