/*!
	CFifoBuffer

	FiFoバッファを実装
	CBufferdSocket用補助クラス
*/
#include "StdAfx.h"
#include "FifoBuffer.h"

/////////////////////////////////////////////////////////////////////////////////////
//	コンストラクタ
/////////////////////////////////////////////////////////////////////////////////////
/*!
	ノーマルコンストラクタ
*/
CFifoBuffer::CFifoBuffer()
{
	m_buf = NULL;
	m_bufLen = 0;
	m_inBufLen = 0;
}

/*!
	コピーコンストラクタ
*/CFifoBuffer::CFifoBuffer(CFifoBuffer &other)
{
	InitBuf(other.m_bufLen);

	m_inBufLen = other.m_inBufLen;
	memmove(m_buf,other.m_buf,m_bufLen);
}

/*!
	デストラクタ
*/CFifoBuffer::~CFifoBuffer(void)
{
	Close();
}


/////////////////////////////////////////////////////////////////////////////////////
//	初期化
/////////////////////////////////////////////////////////////////////////////////////
/*!
	初期化
*/void CFifoBuffer::InitBuf(int bufLen)
{
	Close();

	m_buf = new char[bufLen];
	m_bufLen = bufLen;
	m_inBufLen = 0;
}

/*!
	解放
*/void CFifoBuffer::Close()
{
	if(m_buf)
	{
		delete m_buf;
		m_buf = NULL;
		m_bufLen = 0;
		m_inBufLen = 0;
	}
}


/////////////////////////////////////////////////////////////////////////////////////
//	読み書き
/////////////////////////////////////////////////////////////////////////////////////
/*!
	書き込み
*/
int CFifoBuffer::WriteBuf(const char *data,int dataLen)
{
	//	バッファ一杯？
	if(IsFull())
		return(0);

	//	バッファ容量を超えている？
	if(dataLen > GetFreeBuf())
		dataLen = GetFreeBuf();

	memmove(m_buf + m_inBufLen,data,dataLen);
	m_inBufLen += dataLen;

	//	実際に書かれた量
	return(dataLen);
}

/*!
	読み出し
*/
int CFifoBuffer::ReadBuf(char *data,int dataLen)
{
	//	データ空？
	if(IsEmpty())
		return(0);

	//	データが足りない？
	if(dataLen > GetInBuf())
		dataLen = GetInBuf();

	memmove(data,m_buf,dataLen);

	//	バッファスクロール
	m_inBufLen -= dataLen;
	memmove(m_buf,m_buf + dataLen,m_inBufLen);

	//	実際によまれた量
	return(dataLen);
}


/*!
	読み出し(バッファを消さない)
*/
int CFifoBuffer::PeekBuf(char *data,int dataLen) const
{
	//	データ空？
	if(IsEmpty())
		return(0);

	//	データが足りない？
	if(dataLen > GetInBuf())
		dataLen = GetInBuf();

	memmove(data,m_buf,dataLen);

	//	実際によまれた量
	return(dataLen);
}

/*!
	クリア
*/
void CFifoBuffer::Clear()
{
	m_inBufLen = 0;
}



/////////////////////////////////////////////////////////////////////////////////////
//	バッファアクセス
/////////////////////////////////////////////////////////////////////////////////////
/*!
	書き込み用バッファ取得
*/
char *CFifoBuffer::GetWriteBuffer(int *bufLen)
{
	*bufLen = GetFreeBuf();
	return(m_buf + m_inBufLen);
}

/*!
	読み出し用バッファ取得
*/
char *CFifoBuffer::GetReadBuffer(int *bufLen)
{
	*bufLen = GetInBuf();
	return(m_buf);
}

/*!
	書き込んだ長さを設定
*/
void CFifoBuffer::SetWritedLen(int len)
{
	//	バッファ容量を超えている？
	ASSERT(len <= GetFreeBuf());
	if(len > GetFreeBuf())
		len = GetFreeBuf();

	m_inBufLen += len;
}

/*!
	読み出した長さを設定
*/
void CFifoBuffer::SetReadedLen(int len)
{
	//	バッファ容量を超えている？
	ASSERT(len <= GetInBuf());
	if(len > GetInBuf())
		len = GetInBuf();

	//	バッファスクロール
	m_inBufLen -= len;
	memmove(m_buf,m_buf + len,m_inBufLen);
}


/////////////////////////////////////////////////////////////////////////////////////
//	状態
/////////////////////////////////////////////////////////////////////////////////////
/*!
	バッファが一杯？
*/
int CFifoBuffer::IsFull() const
{
	if(GetFreeBuf()==0)
		return(1);
	return(0);
}

/*!
	バッファが空？
*/
int CFifoBuffer::IsEmpty() const
{
	if(GetInBuf()==0)
		return(1);
	return(0);
}


/*!
	使用容量取得
*/
int CFifoBuffer::GetInBuf() const
{
	return(m_inBufLen);
}

/*!
	空き容量取得
*/
int CFifoBuffer::GetFreeBuf() const
{
	return(m_bufLen - m_inBufLen);
}

