summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/xas/riff.h19
-rw-r--r--src/Makefile4
-rw-r--r--src/riff.c90
3 files changed, 88 insertions, 25 deletions
diff --git a/include/xas/riff.h b/include/xas/riff.h
index 6dc2d8d..bf438cc 100644
--- a/include/xas/riff.h
+++ b/include/xas/riff.h
@@ -4,6 +4,10 @@
#include <stdint.h>
#include <sys/types.h>
+#include <xas/audio.h>
+
+#define XAS_RIFF_WAVE_DEFAULT_TYPE 1
+
typedef struct _xas_riff_chunk {
char id[4];
uint32_t size;
@@ -33,15 +37,12 @@ typedef struct _xas_riff_wave_header {
xas_riff_chunk data;
} xas_riff_wave_header;
-typedef struct _xas_riff {
- int fd;
- size_t size;
-} xas_riff;
-
-xas_riff *xas_riff_open_file(const char *path, int flags);
-
-int xas_riff_close(xas_riff *riff);
+typedef struct _xas_riff xas_riff;
-ssize_t xas_riff_write(xas_riff *riff, void *data, size_t len);
+xas_audio_stream *xas_riff_open_file(const char *path,
+ size_t sample_size,
+ size_t sample_rate,
+ size_t channels,
+ int flags);
#endif /* _XAS_RIFF_H */
diff --git a/src/Makefile b/src/Makefile
index c00ccc0..3046c70 100644
--- a/src/Makefile
+++ b/src/Makefile
@@ -7,9 +7,9 @@ CC = $(CROSS)cc
CFLAGS += -I$(INCLUDE_PATH)
LDFLAGS +=
-HEADERS = riff.h audio.h
+HEADERS = audio.h riff.h
-OBJS = riff.o
+OBJS = audio.o riff.o
VERSION_MAJOR = 0
VERSION_MINOR = 0.1
diff --git a/src/riff.c b/src/riff.c
index 1cf2f85..edacce4 100644
--- a/src/riff.c
+++ b/src/riff.c
@@ -2,8 +2,14 @@
#include <fcntl.h>
#include <unistd.h>
+#include <xas/audio.h>
#include <xas/riff.h>
+struct _xas_riff {
+ int fd;
+ size_t size;
+};
+
static int header_write(xas_riff *riff) {
xas_riff_wave_header header = {
.riff = {
@@ -23,7 +29,7 @@ static int header_write(xas_riff *riff) {
.size = 16
},
- .type = 1,
+ .type = XAS_RIFF_WAVE_DEFAULT_TYPE,
.channels = 1,
.sample_rate = 44100,
.byte_rate = 176400 / 2,
@@ -55,7 +61,11 @@ error_io:
return -1;
}
-xas_riff *xas_riff_open_file(const char *path, int flags) {
+static xas_riff *file_open(const char *path,
+ size_t sample_size,
+ size_t sample_rate,
+ size_t channels,
+ int flags) {
xas_riff *riff;
if ((riff = malloc(sizeof(*riff))) == NULL) {
@@ -71,14 +81,16 @@ xas_riff *xas_riff_open_file(const char *path, int flags) {
riff->size = 0;
- if (header_write(riff) < 0) {
- goto error_header_write;
+ if (flags & (O_CREAT | O_TRUNC)) {
+ if (header_write(riff) < 0) {
+ goto error_header_write;
+ }
}
return riff;
error_header_write:
- (void)close(riff->fd);
+ close(riff->fd);
error_open:
free(riff);
@@ -87,7 +99,7 @@ error_malloc_riff:
return NULL;
}
-int xas_riff_close(xas_riff *riff) {
+static int file_close(xas_riff *riff) {
if (lseek(riff->fd, 0, SEEK_SET) < 0) {
goto error_io;
}
@@ -105,17 +117,67 @@ error_io:
return -1;
}
-ssize_t xas_riff_write(xas_riff *riff, void *data, size_t len) {
- ssize_t wrlen;
+static int audio_drain(xas_riff *riff,
+ void *samples,
+ size_t count,
+ xas_audio_stream *stream) {
+ size_t wrlen = count * stream->sample_size
+ * stream->channels;
+
+ return write(riff->fd, samples, wrlen);
+}
+
+static ssize_t audio_fill(xas_riff *riff,
+ void *samples,
+ size_t count,
+ xas_audio_stream *stream) {
+ ssize_t len = count * stream->sample_size
+ * stream->channels;
+
+ return read(riff->fd, samples, len);
+}
+
+xas_audio_stream *xas_riff_file_open(const char *path,
+ size_t sample_size,
+ size_t sample_rate,
+ size_t channels,
+ int flags) {
+ xas_audio_stream *stream;
+ xas_riff *riff;
- if ((wrlen = write(riff->fd, data, len)) < 0) {
- goto error_write;
+ if ((riff = file_open(path,
+ channels,
+ sample_size,
+ sample_rate,
+ flags)) == NULL) {
+ goto error_file_open;
}
- riff->size += wrlen;
+ if (flags & (O_RDWR | O_WRONLY)) {
+ if ((stream = xas_audio_stream_new_sink((xas_audio_drain)audio_drain,
+ riff,
+ sample_size,
+ sample_rate,
+ channels,
+ 4096)) == NULL) {
+ goto error_audio_stream_new_sink;
+ }
+ } else {
+ if ((stream = xas_audio_stream_new_source((xas_audio_fill)audio_fill,
+ riff,
+ sample_size,
+ sample_rate,
+ channels,
+ 4096)) == NULL) {
+ goto error_audio_stream_new_sink;
+ }
+ }
- return wrlen;
+ return stream;
-error_write:
- return -1;
+error_audio_stream_new_sink:
+ file_close(riff);
+
+error_file_open:
+ return NULL;
}