#include "symbian_tree.h"
#include "pointer.h"

void CGenericIntMap::AddDataL(uint32 Key, void* data)
{
	TBtreePos pos;
	Entry e;
	e.key=Key; e.data=data;
	TBool no_dup=iTree->InsertL(pos, e);
	if (! no_dup && iDeletor) {
		(*iDeletor)(data);
	}
}

void* CGenericIntMap::GetData(uint32 Key)
{
	TBtreePos pos;
	TBool found=iTree->FindL(pos, Key);
	if (found) {
		Entry e;
		iTree->ExtractAtL(pos, e);
		return e.data;
	} else {
		return 0;
	}
}

void CGenericIntMap::DeleteL(uint32 Key)
{
	TBtreePos pos;
	TBool found=iTree->FindL(pos, Key);
	if (found) {
		if (iDeletor) {
			Entry e;
			iTree->ExtractAtL(pos, e);
			(*iDeletor)(e.data);
		}
		iTree->DeleteAtL(pos);
	}
}

CGenericIntMap::~CGenericIntMap()
{
	if (iDeletor) {
		TBtreeMark i;
		TBool more=iTree->ResetL(i);
		Entry e;
		while (more) {
			iTree->ExtractAtL(i, e);
			(*iDeletor)(e.data);
			more=iTree->NextL(i);
		}
	}

	delete iTree;
	delete iPool;
}

int CGenericIntMap::Count() const
{
	return -1;
}

void CGenericIntMap::SetDeletor( void(*delete_func)(void* data) )
{
	iDeletor=delete_func;
}

CGenericIntMap* CGenericIntMap::NewL()
{
	auto_ptr<CGenericIntMap> ret(new (ELeave) CGenericIntMap);
	ret->ConstructL();
	return ret.release();
}

CGenericIntMap::CGenericIntMap()
{
}

void CGenericIntMap::ConstructL()
{
	iTree=new (ELeave) TBtreeFix<Entry, uint32>(EBtreeFast);
	iPool=CMemPagePool::NewL();
	iTree->Connect(iPool, &iKey);
}

void CGenericIntMap::GenKey::Between(const TAny* aLeft,const TAny* aRight,TBtreePivot& aPivot) const
{
	uint32 left=*(uint32*)aLeft;
	uint32 right=*(uint32*)aRight;

	uint32 mid=left+(right-left)/2;
	aPivot.Copy((TUint8*)&mid, sizeof(mid));
}


TInt CGenericIntMap::GenKey::Compare(const TAny* aLeft,const TAny* aRight) const
{
	uint32 left=*(uint32*)aLeft;
	uint32 right=*(uint32*)aRight;

	if (left<right) return -1;
	if (left>right) return 1;
	return 0;
}

const TAny* CGenericIntMap::GenKey::Key(const TAny* anEntry) const
{
	Entry* e=(Entry*)anEntry;
	return (TAny*)&(e->key);
}