#include "mpg123_decoder.h" #include #include #include DecoderMpg123::DecoderMpg123(const std::string& filename) : ifile(filename.c_str()) { int error; handle = mpg123_new("generic", &error); if(error) { throw std::runtime_error(mpg123_plain_strerror(error)); } error = mpg123_open_feed(handle); if(error) { throw std::runtime_error(mpg123_plain_strerror(error)); } mpg123_format_none(handle); mpg123_format(handle, 44100, 2, MPG123_ENC_SIGNED_16); } DecoderMpg123::~DecoderMpg123() { mpg123_close(handle); mpg123_delete(handle); } size_t DecoderMpg123::decode(const uint8_t *input, size_t input_size, uint8_t *output, size_t output_size) { if(mpg123_feed(handle, input, input_size) != MPG123_OK) { throw std::runtime_error(mpg123_strerror(handle)); } size_t output_written; int error = mpg123_read(handle, output, output_size, &output_written); if(error == MPG123_NEW_FORMAT) { long rate; int channels, enc; mpg123_getformat(handle, &rate, &channels, &enc); std::cout << boost::format("mpg123: New format: %li Hz, %i channels, encoding value %i") % rate % channels % enc << std::endl; error = mpg123_read(handle, output, output_size, &output_written); } if(error != MPG123_OK && error != MPG123_DONE && error != MPG123_NEED_MORE) { throw std::runtime_error(mpg123_plain_strerror(error)); } return output_written; } std::size_t DecoderMpg123::read(char* buf, std::size_t buf_size) { char src_data[0x2000]; std::streamsize src_read = ifile.get(src_data, 0x2000).gcount(); if(src_read < 0) src_read = 0; return decode((const uint8_t*)src_data, src_read, (uint8_t*)buf, buf_size); }