summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorcbdev <cb@cbcdn.com>2023-09-25 22:00:50 +0200
committercbdev <cb@cbcdn.com>2023-09-25 22:00:50 +0200
commit3c018eab670be40ffd1841ad9946f5f555b4a76a (patch)
tree8eb05879bc548c0de7cba6b51380a1ac3f584664
parent1a5f7b4f013e7294d40cd8539ae6d9e16ddf423c (diff)
downloadwavextract-3c018eab670be40ffd1841ad9946f5f555b4a76a.tar.gz
wavextract-3c018eab670be40ffd1841ad9946f5f555b4a76a.tar.bz2
wavextract-3c018eab670be40ffd1841ad9946f5f555b4a76a.zip
Refactor header parsing
-rw-r--r--wavextract.c134
1 files changed, 82 insertions, 52 deletions
diff --git a/wavextract.c b/wavextract.c
index 4192f64..137d1a0 100644
--- a/wavextract.c
+++ b/wavextract.c
@@ -61,6 +61,80 @@ static int usage(char* fn){
return EXIT_FAILURE;
}
+int wave_verify_riff(int fd, hdr_riff_t* hdr){
+ if(read(fd, hdr, sizeof(hdr_riff_t)) != sizeof(hdr_riff_t)){
+ fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
+ return 1;
+ }
+
+ if(memcmp(hdr->magic_riff, "RIFF", 4) || memcmp(hdr->magic_wave, "WAVE", 4)){
+ fprintf(stderr, "Invalid RIFF/WAVE magic - probably not a WAVE file\n");
+ return 1;
+ }
+
+ fprintf(stderr, "RIFF chunk size: %d\n", hdr->size);
+ return 0;
+}
+
+int wave_verify_fmt(int fd, hdr_fmt_t* hdr){
+ uint16_t extra_data;
+ uint8_t skip_byte;
+ size_t n;
+
+ if(read(fd, hdr, sizeof(hdr_fmt_t)) != sizeof(hdr_fmt_t)){
+ fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
+ return 1;
+ }
+
+ if(memcmp(hdr->magic, "fmt ", 4)){
+ fprintf(stderr, "Invalid format header magic - format probably incompatible\n");
+ return 1;
+ }
+
+ fprintf(stderr, "Format chunk size: %d\n", hdr->size);
+ fprintf(stderr, "Format: %d\n", hdr->fmt);
+ fprintf(stderr, "Channels: %d\n", hdr->channels);
+ fprintf(stderr, "Samplerate: %d\n", hdr->sample_rate);
+ fprintf(stderr, "Byterate: %d\n", hdr->byte_rate);
+ fprintf(stderr, "Align: %d\n", hdr->bitdepth);
+ fprintf(stderr, "Samplebits: %d\n", hdr->samplebits);
+
+ if(hdr->fmt != 1){
+ if(read(fd, &extra_data, 2) != 2){
+ fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
+ return 1;
+ }
+ }
+ else if(hdr->size > 16 /* length of fmt header as counted from after the size member */){
+ fprintf(stderr, "Skipping %d additional header bytes:", hdr->size - 16);
+ for(n = 16; n < hdr->size; n++){
+ if(read(fd, &skip_byte, 1) != 1){
+ fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
+ return 1;
+ }
+ fprintf(stderr, " %02X", skip_byte);
+ }
+ fprintf(stderr, "\n");
+ }
+
+ return 0;
+}
+
+int wave_verify_data(int fd, hdr_data_t* hdr){
+ if(read(fd, hdr, sizeof(hdr_data_t)) != sizeof(hdr_data_t)){
+ fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
+ return 1;
+ }
+
+ if(memcmp(hdr->magic, "data", 4)){
+ fprintf(stderr, "Invalid data magic\n");
+ return 1;
+ }
+
+ fprintf(stderr, "%d bytes of sample data in file\n", hdr->size);
+ return 0;
+}
+
int main(int argc, char** argv){
size_t n;
#ifdef _WIN32
@@ -79,53 +153,24 @@ int main(int argc, char** argv){
}
hdr_riff_t riff;
- if(read(source_fd, &riff, sizeof(riff)) != sizeof(riff)){
- close(source_fd);
- fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
- return EXIT_FAILURE;
- }
+ hdr_fmt_t fmt;
+ hdr_data_t data;
- if(memcmp(riff.magic_riff, "RIFF", 4) || memcmp(riff.magic_wave, "WAVE", 4)){
+ if(wave_verify_riff(source_fd, &riff)){
close(source_fd);
- fprintf(stderr, "Invalid RIFF/WAVE magic\n");
return EXIT_FAILURE;
}
- fprintf(stderr, "Chunk size: %d\n", riff.size);
-
- hdr_fmt_t fmt;
- uint16_t extra_data;
- if(read(source_fd, &fmt, sizeof(fmt)) != sizeof(fmt)){
+ if(wave_verify_fmt(source_fd, &fmt)){
close(source_fd);
- fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
- return EXIT_FAILURE;
+ return EXIT_FAILURE;
}
- if(memcmp(fmt.magic, "fmt ", 4)){
+ if(wave_verify_data(source_fd, &data)){
close(source_fd);
- fprintf(stderr, "Invalid format magic\n");
return EXIT_FAILURE;
}
- fprintf(stderr, "Format chunk size: %d\n", fmt.size);
- fprintf(stderr, "Format: %d\n", fmt.fmt);
- fprintf(stderr, "Channels: %d\n", fmt.channels);
- fprintf(stderr, "Samplerate: %d\n", fmt.sample_rate);
- fprintf(stderr, "Byterate: %d\n", fmt.byte_rate);
- fprintf(stderr, "Align: %d\n", fmt.bitdepth);
- fprintf(stderr, "Samplebits: %d\n", fmt.samplebits);
-
- if(fmt.fmt != 1){
- read(source_fd, &extra_data, 2);
- }
-
- if(fmt.fmt == 1 && fmt.size > 16){
- fprintf(stderr, "Skipping %d additional header bytes\n", fmt.size - 16);
- for(n = 16; n < fmt.size; n++){
- read(source_fd, &extra_data, 1);
- }
- }
-
/* For now, just skip further analysis and bail on incompatible format */
if(fmt.samplebits != 16){
close(source_fd);
@@ -133,25 +178,10 @@ int main(int argc, char** argv){
return EXIT_FAILURE;
}
- hdr_data_t data_header;
- if(read(source_fd, &data_header, sizeof(data_header)) != sizeof(data_header)){
- close(source_fd);
- fprintf(stderr, "Failed to read input data: %s\n", strerror(errno));
- return EXIT_FAILURE;
- }
-
- if(memcmp(data_header.magic, "data", 4)){
- close(source_fd);
- fprintf(stderr, "Invalid data magic\n");
- return EXIT_FAILURE;
- }
-
- fprintf(stderr, "%d bytes of sample data in file\n", data_header.size);
-
uint16_t sample;
uint8_t channel = 0;
- for(n = 0; n < data_header.size / 2; n++){
+ for(n = 0; n < data.size / 2; n++){
//read sample
if(read(source_fd, &sample, 2) != 2){
close(source_fd);
@@ -175,6 +205,6 @@ int main(int argc, char** argv){
}
close(source_fd);
- fprintf(stderr, "All done\n");
+ fprintf(stderr, "Done, exported %ld frames of data %d channels, processed %ld samples\n", n, fmt.channels, fmt.channels * n);
return EXIT_SUCCESS;
}