output/recorder: use FileOutputStream

This commit is contained in:
Max Kellermann 2015-01-07 19:07:59 +01:00
parent 58c4db925b
commit b7acf86408
1 changed files with 15 additions and 49 deletions

View File

@ -26,17 +26,11 @@
#include "config/ConfigError.hxx" #include "config/ConfigError.hxx"
#include "Log.hxx" #include "Log.hxx"
#include "fs/AllocatedPath.hxx" #include "fs/AllocatedPath.hxx"
#include "fs/FileSystem.hxx" #include "fs/io/FileOutputStream.hxx"
#include "util/Error.hxx" #include "util/Error.hxx"
#include "util/Domain.hxx" #include "util/Domain.hxx"
#include "system/fd_util.h"
#include "open.h"
#include <assert.h> #include <assert.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <errno.h>
struct RecorderOutput { struct RecorderOutput {
AudioOutput base; AudioOutput base;
@ -52,9 +46,9 @@ struct RecorderOutput {
AllocatedPath path; AllocatedPath path;
/** /**
* The destination file descriptor. * The destination file.
*/ */
int fd; FileOutputStream *file;
/** /**
* The buffer for encoder_read(). * The buffer for encoder_read().
@ -76,8 +70,6 @@ struct RecorderOutput {
bool Open(AudioFormat &audio_format, Error &error); bool Open(AudioFormat &audio_format, Error &error);
void Close(); void Close();
bool WriteToFile(const void *data, size_t length, Error &error);
/** /**
* Writes pending data from the encoder to the output file. * Writes pending data from the encoder to the output file.
*/ */
@ -153,36 +145,11 @@ recorder_output_finish(AudioOutput *ao)
delete recorder; delete recorder;
} }
inline bool
RecorderOutput::WriteToFile(const void *_data, size_t length, Error &error)
{
assert(length > 0);
const uint8_t *data = (const uint8_t *)_data, *end = data + length;
while (true) {
ssize_t nbytes = write(fd, data, end - data);
if (nbytes > 0) {
data += nbytes;
if (data == end)
return true;
} else if (nbytes == 0) {
/* shouldn't happen for files */
error.Set(recorder_output_domain,
"write() returned 0");
return false;
} else if (errno != EINTR) {
error.FormatErrno("Failed to write to '%s'",
path.c_str());
return false;
}
}
}
inline bool inline bool
RecorderOutput::EncoderToFile(Error &error) RecorderOutput::EncoderToFile(Error &error)
{ {
assert(fd >= 0); assert(file != nullptr);
assert(file->IsDefined());
while (true) { while (true) {
/* read from the encoder */ /* read from the encoder */
@ -193,7 +160,7 @@ RecorderOutput::EncoderToFile(Error &error)
/* write everything into the file */ /* write everything into the file */
if (!WriteToFile(buffer, size, error)) if (!file->Write(buffer, size, error))
return false; return false;
} }
} }
@ -203,26 +170,22 @@ RecorderOutput::Open(AudioFormat &audio_format, Error &error)
{ {
/* create the output file */ /* create the output file */
fd = OpenFile(path, file = new FileOutputStream(path, error);
O_CREAT|O_WRONLY|O_TRUNC|O_BINARY, if (!file->IsDefined()) {
0666); delete file;
if (fd < 0) {
error.FormatErrno("Failed to create '%s'", path.c_str());
return false; return false;
} }
/* open the encoder */ /* open the encoder */
if (!encoder_open(encoder, audio_format, error)) { if (!encoder_open(encoder, audio_format, error)) {
close(fd); delete file;
RemoveFile(path);
return false; return false;
} }
if (!EncoderToFile(error)) { if (!EncoderToFile(error)) {
encoder_close(encoder); encoder_close(encoder);
close(fd); delete file;
RemoveFile(path);
return false; return false;
} }
@ -241,7 +204,10 @@ RecorderOutput::Commit(Error &error)
encoder_close(encoder); encoder_close(encoder);
close(fd); if (success && !file->Commit(error))
success = false;
delete file;
return success; return success;
} }