* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#if HAVE_CONFIG_H
# include <config.h>
#endif
-#if defined _WIN32 && !defined __CYGWIN__
-/* where MSVC puts unlink() */
-# include <io.h>
-#else
-# include <unistd.h>
-#endif
-#if defined _MSC_VER || defined __MINGW32__
-#include <sys/types.h> /* for off_t */
-#if _MSC_VER <= 1600 /* @@@ [2G limit] */
-#define fseeko fseek
-#define ftello ftell
-#endif
-#endif
#include <errno.h>
#include <limits.h> /* for LONG_MAX */
#include <math.h> /* for floor() */
#include <stdio.h> /* for FILE etc. */
#include <stdlib.h> /* for malloc */
#include <string.h> /* for strcmp(), strerror() */
+#include <sys/stat.h>
#include "FLAC/all.h"
#include "share/alloc.h"
#include "share/grabbag.h"
+#include "share/compat.h"
+#include "share/private.h"
#include "encode.h"
#ifdef min
/* this is the client_data attached to the FLAC decoder when encoding from a FLAC file */
typedef struct {
- off_t filesize;
+ FLAC__off_t filesize;
const FLAC__byte *lookahead;
unsigned lookahead_length;
size_t num_metadata_blocks;
/*
- * unpublished debug routines from the FLAC libs
- */
-extern FLAC__bool FLAC__stream_encoder_disable_constant_subframes(FLAC__StreamEncoder *encoder, FLAC__bool value);
-extern FLAC__bool FLAC__stream_encoder_disable_fixed_subframes(FLAC__StreamEncoder *encoder, FLAC__bool value);
-extern FLAC__bool FLAC__stream_encoder_disable_verbatim_subframes(FLAC__StreamEncoder *encoder, FLAC__bool value);
-extern FLAC__bool FLAC__stream_encoder_set_do_md5(FLAC__StreamEncoder *encoder, FLAC__bool value);
-
-/*
* local routines
*/
-static FLAC__bool EncoderSession_construct(EncoderSession *e, encode_options_t options, off_t infilesize, FILE *infile, const char *infilename, const char *outfilename, const FLAC__byte *lookahead, unsigned lookahead_length);
+static FLAC__bool EncoderSession_construct(EncoderSession *e, encode_options_t options, FLAC__off_t infilesize, FILE *infile, const char *infilename, const char *outfilename, const FLAC__byte *lookahead, unsigned lookahead_length);
static void EncoderSession_destroy(EncoderSession *e);
static int EncoderSession_finish_ok(EncoderSession *e, int info_align_carry, int info_align_zero, foreign_metadata_t *foreign_metadata);
static int EncoderSession_finish_error(EncoderSession *e);
FLAC__uint16 x;
FLAC__uint32 xx, data_bytes;
FLAC__uint16 wFormatTag; /* wFormatTag word from the 'fmt ' chunk */
- unsigned block_align;
if(got_fmt_chunk) {
flac__utils_printf(stderr, 1, "%s: ERROR: file has multiple 'fmt ' chunks\n", e->inbasefilename);
/* block align */
if(!read_uint16(e->fin, /*big_endian=*/false, &x, e->inbasefilename))
return false;
- block_align = (unsigned)x;
+
/* bits per sample */
if(!read_uint16(e->fin, /*big_endian=*/false, &x, e->inbasefilename))
return false;
}
else if(
channel_mask == 0x003f || /* 6 channels: front left, front right, front center, LFE, back left, back right */
- channel_mask == 0x060f /* 6 channels: front left, front right, front center, LFE, side left, side right */
+ channel_mask == 0x060f || /* 6 channels: front left, front right, front center, LFE, side left, side right */
+ channel_mask == 0x070f || /* 7 channels: front left, front right, front center, LFE, back center, side left, side right */
+ channel_mask == 0x063f /* 8 channels: front left, front right, front center, LFE, back left, back right, side left, side right */
) {
/* to dolby order: front left, center, front right, surround left, surround right, LFE */
channel_map[1] = 2;
channel_mask == 0x0037 || /* 5 channels: front left, front right, front center, back left, back right */
channel_mask == 0x0607 || /* 5 channels: front left, front right, front center, side left, side right */
channel_mask == 0x003f || /* 6 channels: front left, front right, front center, LFE, back left, back right */
- channel_mask == 0x060f /* 6 channels: front left, front right, front center, LFE, side left, side right */
+ channel_mask == 0x060f || /* 6 channels: front left, front right, front center, LFE, side left, side right */
+ channel_mask == 0x070f || /* 7 channels: front left, front right, front center, LFE, back center, side left, side right */
+ channel_mask == 0x063f /* 8 channels: front left, front right, front center, LFE, back left, back right, side left, side right */
) {
/* keep default channel order */
}
/*
* public routines
*/
-int flac__encode_file(FILE *infile, off_t infilesize, const char *infilename, const char *outfilename, const FLAC__byte *lookahead, unsigned lookahead_length, encode_options_t options)
+int flac__encode_file(FILE *infile, FLAC__off_t infilesize, const char *infilename, const char *outfilename, const FLAC__byte *lookahead, unsigned lookahead_length, encode_options_t options)
{
EncoderSession encoder_session;
size_t channel_map[FLAC__MAX_CHANNELS];
/* adjust encoding parameters based on skip and until values */
switch(options.format) {
case FORMAT_RAW:
- infilesize -= (off_t)skip * encoder_session.info.bytes_per_wide_sample;
+ infilesize -= (FLAC__off_t)skip * encoder_session.info.bytes_per_wide_sample;
encoder_session.total_samples_to_encode = total_samples_in_input - skip;
break;
case FORMAT_WAVE:
FLAC__ASSERT(total_samples_in_input > 0);
FLAC__ASSERT(!options.sector_align);
if(options.format == FORMAT_RAW)
- infilesize -= (off_t)trim * encoder_session.info.bytes_per_wide_sample;
+ infilesize -= (FLAC__off_t)trim * encoder_session.info.bytes_per_wide_sample;
else if(EncoderSession_format_is_iff(&encoder_session))
encoder_session.fmt.iff.data_bytes -= trim * encoder_session.info.bytes_per_wide_sample;
encoder_session.total_samples_to_encode -= trim;
*options.align_reservoir_samples = align_remainder;
if(options.format == FORMAT_RAW) {
FLAC__ASSERT(infilesize >= 0);
- infilesize -= (off_t)((*options.align_reservoir_samples) * encoder_session.info.bytes_per_wide_sample);
+ infilesize -= (FLAC__off_t)((*options.align_reservoir_samples) * encoder_session.info.bytes_per_wide_sample);
FLAC__ASSERT(infilesize >= 0);
}
else if(EncoderSession_format_is_iff(&encoder_session))
return EncoderSession_finish_error(&encoder_session);
}
else if(feof(infile)) {
- flac__utils_printf(stderr, 1, "%s: WARNING: unexpected EOF; expected %u samples, got %u samples\n", encoder_session.inbasefilename, (unsigned)encoder_session.total_samples_to_encode, (unsigned)encoder_session.samples_written);
+ flac__utils_printf(stderr, 1, "%s: WARNING: unexpected EOF; expected %" PRIu64 " samples, got %" PRIu64 " samples\n", encoder_session.inbasefilename, encoder_session.total_samples_to_encode, encoder_session.samples_written);
if(encoder_session.treat_warnings_as_errors)
return EncoderSession_finish_error(&encoder_session);
total_input_bytes_read = max_input_bytes;
}
else if(feof(infile)) {
if(options.ignore_chunk_sizes) {
- flac__utils_printf(stderr, 1, "%s: INFO: hit EOF with --ignore-chunk-sizes, got %u samples\n", encoder_session.inbasefilename, (unsigned)encoder_session.samples_written);
+ flac__utils_printf(stderr, 1, "%s: INFO: hit EOF with --ignore-chunk-sizes, got %" PRIu64 " samples\n", encoder_session.inbasefilename, encoder_session.samples_written);
}
else {
- flac__utils_printf(stderr, 1, "%s: WARNING: unexpected EOF; expected %u samples, got %u samples\n", encoder_session.inbasefilename, (unsigned)encoder_session.total_samples_to_encode, (unsigned)encoder_session.samples_written);
+ flac__utils_printf(stderr, 1, "%s: WARNING: unexpected EOF; expected %" PRIu64 " samples, got %" PRIu64 " samples\n", encoder_session.inbasefilename, encoder_session.total_samples_to_encode, encoder_session.samples_written);
if(encoder_session.treat_warnings_as_errors)
return EncoderSession_finish_error(&encoder_session);
}
return EncoderSession_finish_error(&encoder_session);
}
else if(bytes_read != (*options.align_reservoir_samples) * encoder_session.info.bytes_per_wide_sample) {
- flac__utils_printf(stderr, 1, "%s: WARNING: unexpected EOF; read %u bytes; expected %u samples, got %u samples\n", encoder_session.inbasefilename, (unsigned)bytes_read, (unsigned)encoder_session.total_samples_to_encode, (unsigned)encoder_session.samples_written);
+ flac__utils_printf(stderr, 1, "%s: WARNING: unexpected EOF; read %" PRIu64 " bytes; expected %" PRIu64 " samples, got %" PRIu64 " samples\n", encoder_session.inbasefilename, bytes_read, encoder_session.total_samples_to_encode, encoder_session.samples_written);
if(encoder_session.treat_warnings_as_errors)
return EncoderSession_finish_error(&encoder_session);
}
);
}
-FLAC__bool EncoderSession_construct(EncoderSession *e, encode_options_t options, off_t infilesize, FILE *infile, const char *infilename, const char *outfilename, const FLAC__byte *lookahead, unsigned lookahead_length)
+FLAC__bool EncoderSession_construct(EncoderSession *e, encode_options_t options, FLAC__off_t infilesize, FILE *infile, const char *infilename, const char *outfilename, const FLAC__byte *lookahead, unsigned lookahead_length)
{
unsigned i;
FLAC__uint32 test = 1;
FLAC__StreamMetadata padding;
FLAC__StreamMetadata **metadata = 0;
static_metadata_t static_metadata;
- unsigned num_metadata = 0, i;
+ unsigned num_metadata = 0, ic;
FLAC__StreamEncoderInitStatus init_status;
const FLAC__bool is_cdda = (channels == 1 || channels == 2) && (bps == 16) && (sample_rate == 44100);
char apodizations[2000];
* metadata as the basis for the encoded file
*/
{
+ unsigned i;
/*
* first handle pictures: simple append any --pictures
* specified.
* from scratch
*/
const foreign_metadata_t *foreign_metadata = EncoderSession_format_is_iff(e)? options.format_options.iff.foreign_metadata : 0;
+ unsigned i;
if(e->seek_table_template->data.seek_table.num_points > 0) {
e->seek_table_template->is_last = false; /* the encoder will set this for us */
FLAC__stream_encoder_set_channels(e->encoder, channels);
FLAC__stream_encoder_set_bits_per_sample(e->encoder, bps);
FLAC__stream_encoder_set_sample_rate(e->encoder, sample_rate);
- for(i = 0; i < options.num_compression_settings; i++) {
- switch(options.compression_settings[i].type) {
+ for(ic = 0; ic < options.num_compression_settings; ic++) {
+ switch(options.compression_settings[ic].type) {
case CST_BLOCKSIZE:
- FLAC__stream_encoder_set_blocksize(e->encoder, options.compression_settings[i].value.t_unsigned);
+ FLAC__stream_encoder_set_blocksize(e->encoder, options.compression_settings[ic].value.t_unsigned);
break;
case CST_COMPRESSION_LEVEL:
- FLAC__stream_encoder_set_compression_level(e->encoder, options.compression_settings[i].value.t_unsigned);
+ FLAC__stream_encoder_set_compression_level(e->encoder, options.compression_settings[ic].value.t_unsigned);
apodizations[0] = '\0';
break;
case CST_DO_MID_SIDE:
- FLAC__stream_encoder_set_do_mid_side_stereo(e->encoder, options.compression_settings[i].value.t_bool);
+ FLAC__stream_encoder_set_do_mid_side_stereo(e->encoder, options.compression_settings[ic].value.t_bool);
break;
case CST_LOOSE_MID_SIDE:
- FLAC__stream_encoder_set_loose_mid_side_stereo(e->encoder, options.compression_settings[i].value.t_bool);
+ FLAC__stream_encoder_set_loose_mid_side_stereo(e->encoder, options.compression_settings[ic].value.t_bool);
break;
case CST_APODIZATION:
- if(strlen(apodizations)+strlen(options.compression_settings[i].value.t_string)+2 >= sizeof(apodizations)) {
+ if(strlen(apodizations)+strlen(options.compression_settings[ic].value.t_string)+2 >= sizeof(apodizations)) {
flac__utils_printf(stderr, 1, "%s: ERROR: too many apodization functions requested\n", e->inbasefilename);
static_metadata_clear(&static_metadata);
return false;
}
else {
- strcat(apodizations, options.compression_settings[i].value.t_string);
+ strcat(apodizations, options.compression_settings[ic].value.t_string);
strcat(apodizations, ";");
}
break;
case CST_MAX_LPC_ORDER:
- FLAC__stream_encoder_set_max_lpc_order(e->encoder, options.compression_settings[i].value.t_unsigned);
+ FLAC__stream_encoder_set_max_lpc_order(e->encoder, options.compression_settings[ic].value.t_unsigned);
break;
case CST_QLP_COEFF_PRECISION:
- FLAC__stream_encoder_set_qlp_coeff_precision(e->encoder, options.compression_settings[i].value.t_unsigned);
+ FLAC__stream_encoder_set_qlp_coeff_precision(e->encoder, options.compression_settings[ic].value.t_unsigned);
break;
case CST_DO_QLP_COEFF_PREC_SEARCH:
- FLAC__stream_encoder_set_do_qlp_coeff_prec_search(e->encoder, options.compression_settings[i].value.t_bool);
+ FLAC__stream_encoder_set_do_qlp_coeff_prec_search(e->encoder, options.compression_settings[ic].value.t_bool);
break;
case CST_DO_ESCAPE_CODING:
- FLAC__stream_encoder_set_do_escape_coding(e->encoder, options.compression_settings[i].value.t_bool);
+ FLAC__stream_encoder_set_do_escape_coding(e->encoder, options.compression_settings[ic].value.t_bool);
break;
case CST_DO_EXHAUSTIVE_MODEL_SEARCH:
- FLAC__stream_encoder_set_do_exhaustive_model_search(e->encoder, options.compression_settings[i].value.t_bool);
+ FLAC__stream_encoder_set_do_exhaustive_model_search(e->encoder, options.compression_settings[ic].value.t_bool);
break;
case CST_MIN_RESIDUAL_PARTITION_ORDER:
- FLAC__stream_encoder_set_min_residual_partition_order(e->encoder, options.compression_settings[i].value.t_unsigned);
+ FLAC__stream_encoder_set_min_residual_partition_order(e->encoder, options.compression_settings[ic].value.t_unsigned);
break;
case CST_MAX_RESIDUAL_PARTITION_ORDER:
- FLAC__stream_encoder_set_max_residual_partition_order(e->encoder, options.compression_settings[i].value.t_unsigned);
+ FLAC__stream_encoder_set_max_residual_partition_order(e->encoder, options.compression_settings[ic].value.t_unsigned);
break;
case CST_RICE_PARAMETER_SEARCH_DIST:
- FLAC__stream_encoder_set_rice_parameter_search_dist(e->encoder, options.compression_settings[i].value.t_unsigned);
+ FLAC__stream_encoder_set_rice_parameter_search_dist(e->encoder, options.compression_settings[ic].value.t_unsigned);
break;
}
}
EncoderSession *e = (EncoderSession*)client_data;
(void)decoder;
- if(fseeko(e->fin, (off_t)absolute_byte_offset, SEEK_SET) < 0)
+ if(fseeko(e->fin, (FLAC__off_t)absolute_byte_offset, SEEK_SET) < 0)
return FLAC__STREAM_DECODER_SEEK_STATUS_ERROR;
else
return FLAC__STREAM_DECODER_SEEK_STATUS_OK;
FLAC__StreamDecoderTellStatus flac_decoder_tell_callback(const FLAC__StreamDecoder *decoder, FLAC__uint64 *absolute_byte_offset, void *client_data)
{
EncoderSession *e = (EncoderSession*)client_data;
- off_t pos;
+ FLAC__off_t pos;
(void)decoder;
if((pos = ftello(e->fin)) < 0)
FLAC__ASSERT(encoder_session->total_samples_to_encode > 0);
if(samples_written == encoder_session->total_samples_to_encode) {
- flac__utils_printf(stderr, 2, "\r%s:%s wrote %u bytes, ratio=",
+ flac__utils_printf(stderr, 2, "\r%s:%s wrote %" PRIu64 " bytes, ratio=",
encoder_session->inbasefilename,
encoder_session->verify? " Verify OK," : "",
- (unsigned)encoder_session->bytes_written
+ encoder_session->bytes_written
);
}
else {
FLAC__stream_encoder_get_verify_decoder_error_stats(e->encoder, &absolute_sample, &frame_number, &channel, &sample, &expected, &got);
flac__utils_printf(stderr, 1, "%s: ERROR: mismatch in decoded data, verify FAILED!\n", e->inbasefilename);
- flac__utils_printf(stderr, 1, " Absolute sample=%u, frame=%u, channel=%u, sample=%u, expected %d, got %d\n", (unsigned)absolute_sample, frame_number, channel, sample, expected, got);
+ flac__utils_printf(stderr, 1, " Absolute sample=%" PRIu64 ", frame=%u, channel=%u, sample=%u, expected %d, got %d\n", absolute_sample, frame_number, channel, sample, expected, got);
flac__utils_printf(stderr, 1, " In all known cases, verify errors are caused by hardware problems,\n");
flac__utils_printf(stderr, 1, " usually overclocking or bad RAM. Delete %s\n", e->outfilename);
flac__utils_printf(stderr, 1, " and repeat the flac command exactly as before. If it does not give a\n");
FLAC__bool fskip_ahead(FILE *f, FLAC__uint64 offset)
{
static unsigned char dump[8192];
+ struct stat stb;
-#ifdef _MSC_VER
- if(f == stdin) {
- /* MS' stdio impl can't even seek forward on stdin, have to use pure non-fseek() version: */
- while(offset > 0) {
- const long need = (long)min(offset, sizeof(dump));
- if((long)fread(dump, 1, need, f) < need)
- return false;
- offset -= need;
- }
- }
- else
-#endif
+ if(fstat(fileno(f), &stb) == 0 && (stb.st_mode & S_IFMT) == S_IFREG)
{
- while(offset > 0) {
- long need = (long)min(offset, LONG_MAX);
- if(fseeko(f, need, SEEK_CUR) < 0) {
- need = (long)min(offset, sizeof(dump));
- if((long)fread(dump, 1, need, f) < need)
- return false;
- }
- offset -= need;
- }
+ if(fseeko(f, offset, SEEK_CUR) == 0)
+ return true;
+ }
+ while(offset > 0) {
+ const long need = (long)min(offset, sizeof(dump));
+ if((long)fread(dump, 1, need, f) < need)
+ return false;
+ offset -= need;
}
return true;
}