os/persistentdata/persistentstorage/dbms/pcdbms/ustor/US_RCOVR.CPP
changeset 0 bde4ae8d615e
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/os/persistentdata/persistentstorage/dbms/pcdbms/ustor/US_RCOVR.CPP	Fri Jun 15 03:10:57 2012 +0200
     1.3 @@ -0,0 +1,155 @@
     1.4 +// Copyright (c) 1998-2009 Nokia Corporation and/or its subsidiary(-ies).
     1.5 +// All rights reserved.
     1.6 +// This component and the accompanying materials are made available
     1.7 +// under the terms of "Eclipse Public License v1.0"
     1.8 +// which accompanies this distribution, and is available
     1.9 +// at the URL "http://www.eclipse.org/legal/epl-v10.html".
    1.10 +//
    1.11 +// Initial Contributors:
    1.12 +// Nokia Corporation - initial contribution.
    1.13 +//
    1.14 +// Contributors:
    1.15 +//
    1.16 +// Description:
    1.17 +//
    1.18 +
    1.19 +#include "US_STD.H"
    1.20 +#include "U32STD_DBMS.H"
    1.21 +
    1.22 +// Class CDbStoreIndex::CRecover
    1.23 +
    1.24 +NONSHARABLE_CLASS(CDbStoreIndex::CRecover) : public CDbTableDatabase::CStepper
    1.25 +	{
    1.26 +private:
    1.27 +	enum {EClearStep=1};
    1.28 +public:
    1.29 +	CRecover(CDbStoreDatabase& aDatabase,const CDbStoreDef& aTable,const CDbStoreIndexDef& anIndex);
    1.30 +	~CRecover();
    1.31 +	static inline TInt Steps(TInt aCardinality);
    1.32 +private:
    1.33 +	TInt StepL(TInt aStep);
    1.34 +private:
    1.35 +	CDbStoreDatabase& iDatabase;
    1.36 +	const CDbStoreDef& iTable;
    1.37 +	const CDbStoreIndexDef& iIndex;
    1.38 +	CDbTableDatabase::CBuildIndex* iBuild;
    1.39 +	};
    1.40 +
    1.41 +inline TInt CDbStoreIndex::CRecover::Steps(TInt aCardinality)
    1.42 +	{return CDbTableDatabase::CBuildIndex::Steps(aCardinality)+EClearStep;}
    1.43 +
    1.44 +CDbStoreIndex::CRecover::CRecover(CDbStoreDatabase& aDatabase,const CDbStoreDef& aTable,const CDbStoreIndexDef& anIndex)
    1.45 +	: iDatabase(aDatabase),iTable(aTable),iIndex(anIndex)
    1.46 +	{}
    1.47 +
    1.48 +CDbStoreIndex::CRecover::~CRecover()
    1.49 +	{
    1.50 +	delete iBuild;
    1.51 +	}
    1.52 +
    1.53 +TInt CDbStoreIndex::CRecover::StepL(TInt aStep)
    1.54 +	{
    1.55 +	if (iBuild==NULL)
    1.56 +		{	// first step
    1.57 +		iBuild=CDbTableDatabase::CBuildIndex::NewL(iDatabase,iTable,iIndex);
    1.58 +		((CDbStoreIndex&)iBuild->Index()).DiscardL();
    1.59 +		return aStep-EClearStep;
    1.60 +		}
    1.61 +	aStep=iBuild->StepL(aStep);
    1.62 +	if (aStep==0)
    1.63 +		{	// final step
    1.64 +		iDatabase.IndexRecoveredL();
    1.65 +		delete iBuild;
    1.66 +		iBuild=NULL;
    1.67 +		}
    1.68 +	return aStep;
    1.69 +	}
    1.70 +
    1.71 +// Class CDbStoreIndex::CRepair
    1.72 +
    1.73 +NONSHARABLE_CLASS(CDbStoreIndex::CRepair) : public CDbTableDatabase::CStepper
    1.74 +	{
    1.75 +private:
    1.76 +	enum {ERepairStep=1};
    1.77 +public:
    1.78 +	CRepair(CDbStoreDatabase& aDatabase,const CDbStoreDef& aTable,const CDbStoreIndexDef& anIndex);
    1.79 +	static inline TInt Steps();
    1.80 +private:
    1.81 +	TInt StepL(TInt aStep);
    1.82 +private:
    1.83 +	CDbStoreDatabase& iDatabase;
    1.84 +	const CDbStoreDef& iTable;
    1.85 +	const CDbStoreIndexDef& iIndex;
    1.86 +	};
    1.87 +
    1.88 +inline TInt CDbStoreIndex::CRepair::Steps()
    1.89 +	{return ERepairStep;}
    1.90 +
    1.91 +CDbStoreIndex::CRepair::CRepair(CDbStoreDatabase& aDatabase,const CDbStoreDef& aTable,const CDbStoreIndexDef& anIndex)
    1.92 +	: iDatabase(aDatabase),iTable(aTable),iIndex(anIndex)
    1.93 +	{}
    1.94 +
    1.95 +TInt CDbStoreIndex::CRepair::StepL(TInt)
    1.96 +	{
    1.97 +	CDbStoreIndex* index=CDbStoreIndex::NewL(iDatabase,iIndex,iTable);
    1.98 +	CleanupStack::PushL(index);
    1.99 +	index->OpenL();
   1.100 +	index->RepairL();
   1.101 +	CleanupStack::PopAndDestroy();
   1.102 +	return 0;
   1.103 +	}
   1.104 +
   1.105 +// Class CDbStoreDatabase
   1.106 +
   1.107 +CDbTableDatabase::CStepper* CDbStoreDatabase::RecoverL(TInt& aStep)
   1.108 +	{
   1.109 +	TSglQueIterC<CDbStoreDef> iter(SchemaL());	// ensure we have the schema
   1.110 +	TInt count=0;
   1.111 +	const CDbStoreDef* tDef;
   1.112 +	while ((tDef=iter++)!=NULL)
   1.113 +		count+=tDef->Indexes().Count();
   1.114 +	CMultiStepper* mStepper=CMultiStepper::NewL(count);
   1.115 +	CleanupStack::PushL(mStepper);
   1.116 +// damaged ones first (as they are invoked last
   1.117 +	count=0;
   1.118 +	iter.SetToFirst();
   1.119 +	while ((tDef=iter++)!=NULL)
   1.120 +		{
   1.121 +		TInt records=CDbStoreRecords::CardinalityL(Store(),*tDef);
   1.122 +		TSglQueIterC<CDbStoreIndexDef> xIter(tDef->Indexes().AsQue());
   1.123 +		for (const CDbStoreIndexDef* xDef;(xDef=xIter++)!=NULL;)
   1.124 +			{
   1.125 +			if (!CDbStoreIndex::IsDamagedL(*this,*xDef))
   1.126 +				continue;
   1.127 +			// rebuild from scratch
   1.128 +			CDbStoreIndex::CRecover* rebuild=new(ELeave) CDbStoreIndex::CRecover(*this,*tDef,*xDef);
   1.129 +			mStepper->AddStepper(rebuild,rebuild->Steps(records));
   1.130 +			++count;
   1.131 +			}
   1.132 +		}
   1.133 +	if (count==0)
   1.134 +		{	// no indexes are actually damaged
   1.135 +		aStep=0;
   1.136 +		CleanupStack::PopAndDestroy();
   1.137 +		return NULL;
   1.138 +		}
   1.139 +	// repair the other ones after a reclaim
   1.140 +	iter.SetToFirst();
   1.141 +	while ((tDef=iter++)!=NULL)
   1.142 +		{
   1.143 +		TSglQueIterC<CDbStoreIndexDef> xIter(tDef->Indexes().AsQue());
   1.144 +		for (const CDbStoreIndexDef* xDef;(xDef=xIter++)!=NULL;)
   1.145 +			{
   1.146 +			if (CDbStoreIndex::IsDamagedL(*this,*xDef))
   1.147 +				continue;
   1.148 +			// repair from sequence set
   1.149 +			CDbStoreIndex::CRepair* repair=new(ELeave) CDbStoreIndex::CRepair(*this,*tDef,*xDef);
   1.150 +			mStepper->AddStepper(repair,repair->Steps());
   1.151 +			}
   1.152 +		}
   1.153 +	iPagePool->Discard();
   1.154 +	iPagePool->ReclaimAllL();	// recover all page pool space
   1.155 +	aStep=mStepper->TotalSteps();
   1.156 +	CleanupStack::Pop();
   1.157 +	return mStepper;
   1.158 +	}