/*-------------------------------------------------------------------------
   Buf function copy right information

   Copyright (C) 2006-2008. Lin, Rongrong <woody@palmmicro.com>
                            Tang, Li      <tangli@palmmicro.com>

   This program is free software; you can redistribute it and/or
   modify it under the terms of the GNU Lesser General Public
   License as published by the Free Software Foundation; either
   version 2.1 of the License, or (at your option) any later version.

   This software is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   Lesser General Public License for more details.

   You should have received a copy of the GNU Lesser General Public
   License along with this library; if not, write to the Free Software
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
-------------------------------------------------------------------------*/

#include "type.h"
#include "ar168.h"
#include "core.h"

USHORT _sBufPos;

void BufCopyDM2PM()
{
	UCHAR i, j;
	UCHAR pBuf[256];
	PCHAR pCur;

	for (i = 0; i < 3; i ++)
	{
		pCur = (PCHAR)SRAM_BASE;
		for (j = 0; j < 63; j ++)
		{
			SetMemoryPage(_cMemoryPages[i+3]);
			memcpy(pBuf, pCur, 256);
			SetMemoryPage(_cMemoryPages[i]);
			memcpy(pCur, pBuf, 256);
			pCur += 256;
		}
	}
	SetMemoryPage(DEFAULT_MEMORY_PAGE);
}

void BufForward(USHORT sLen)
{
	_sBufPos += sLen;
}

void BufSeek(USHORT sOffset)
{
	_sBufPos = sOffset;
}

/* sLen can't exceed 0x2000 */
void _BufReadWrite(PCHAR pBuf, USHORT sLen, BOOLEAN bWrite)
{
	UCHAR iPageS, iPageE;
	USHORT sLen1, sLen2;
	PCHAR pSram;

	if (!sLen)		return;

	iPageS = _sBufPos >> 14;
	iPageE = (_sBufPos + sLen) >> 14;

	if (iPageS == iPageE)
	{
		sLen1 = sLen;
		sLen2 = 0;
	}
	else
	{
		sLen1 = (iPageE << 14) - _sBufPos;
		sLen2 = sLen - sLen1;
	}

	SetMemoryPage(_cMemoryPages[iPageS]);
	pSram = (PCHAR)(SRAM_BASE + _sBufPos - (iPageS << 14)); 
	if (bWrite)
	{
		memcpy(pSram, pBuf, sLen1);
	}
	else
	{
		memcpy(pBuf, pSram, sLen1);
	}

	if (sLen2)
	{
		SetMemoryPage(_cMemoryPages[iPageE]);
		pBuf += sLen1;
		if (bWrite)
		{
			memcpy((PCHAR)SRAM_BASE, pBuf, sLen2);
		}
		else
		{
			memcpy(pBuf, (PCHAR)SRAM_BASE, sLen2);
		}
	}
	SetMemoryPage(DEFAULT_MEMORY_PAGE);
}

void BufWrite(PCHAR pBuf, USHORT sLen)
{
	_BufReadWrite(pBuf, sLen, TRUE);
}

void BufRead(PCHAR pBuf, USHORT sLen)
{
	_BufReadWrite(pBuf, sLen, FALSE);
}
