#include "AudioFile.h"

using std::string;
using namespace ALWrapper;

const unsigned long AudioFile::defaultbufsize = 8192;

//The default constructor just initializes parameters.
AudioFile::AudioFile() : filesize(0), length(0), bitrate(0),
channels(0), frequency(0), file(0) {}

//The destructor just closes the file.
AudioFile::~AudioFile() { close(); }

//Performs the basic step of creating a stream from a filename.
//Further steps will be needed; these are in the derived class open() functions.
void AudioFile::openfile(const string& fname, const string& mode)
{
	close();
	file = fopen(fname.c_str(), mode.c_str());
	if (file == 0)
		//There was an error opening the file.
		throw AudioFileError(errno, strerror(errno));
	
	filename = fname;
}

//Closes an open file.
void AudioFile::close()
{
	if (isOpen())
		fclose(file);

	file = 0;
}

//Reads the specified amount of data into a buffer.
//This will probably need to be overridden in derived classes that may not
//necessarily use a FILE object to read.
Buffer AudioFile::readData(unsigned long bufsize)
{
	assert(isOpen());
	
	char* buf = new char[bufsize];	//Allocate space to read into.
	unsigned int bytesprocessed = fread(buf, bufsize,
	sizeof(buf[0]), file);
	
	if (bytesprocessed == 0)
		throw AudioFileError(errno, strerror(errno));

	//The buffer that will be filled and returned.
	Buffer ret(buf, bytesprocessed);
	
	delete [] buf;	//Delete the old copy of the data.

	return ret;
}

//Seeks to a particular location in the file.
void AudioFile::seek(unsigned long pos)
{
	assert(isOpen());	
	fseek(file, pos, SEEK_SET);
}

//Returns the current position in the file.
unsigned long AudioFile::tell()
{
	long ret = ftell(file);
	if (ret < 0)
		throw AudioFileError(errno, strerror(errno));

	return ret;
}

