os/persistentdata/persistentstorage/dbms/udbms/UD_ROW.CPP
author sl
Tue, 10 Jun 2014 14:32:02 +0200
changeset 1 260cb5ec6c19
permissions -rw-r--r--
Update contrib.
sl@0
     1
// Copyright (c) 1998-2009 Nokia Corporation and/or its subsidiary(-ies).
sl@0
     2
// All rights reserved.
sl@0
     3
// This component and the accompanying materials are made available
sl@0
     4
// under the terms of "Eclipse Public License v1.0"
sl@0
     5
// which accompanies this distribution, and is available
sl@0
     6
// at the URL "http://www.eclipse.org/legal/epl-v10.html".
sl@0
     7
//
sl@0
     8
// Initial Contributors:
sl@0
     9
// Nokia Corporation - initial contribution.
sl@0
    10
//
sl@0
    11
// Contributors:
sl@0
    12
//
sl@0
    13
// Description:
sl@0
    14
//
sl@0
    15
sl@0
    16
#include "UD_STD.H"
sl@0
    17
sl@0
    18
#define UNUSED_VAR(a) a = a
sl@0
    19
sl@0
    20
// Class TDbColumn
sl@0
    21
sl@0
    22
EXPORT_C void TDbColumn::SetL(const TAny* aPtr,TInt aSize)
sl@0
    23
	{
sl@0
    24
	Mem::Copy(Row().SetColumnWidthL(iColumn,aSize),aPtr,aSize);
sl@0
    25
	}
sl@0
    26
sl@0
    27
EXPORT_C void TDbColumn::SetL(TUint32 aValue)
sl@0
    28
	{
sl@0
    29
	*(TUint32*)Row().SetColumnWidthL(iColumn,sizeof(aValue))=aValue;
sl@0
    30
	}
sl@0
    31
sl@0
    32
EXPORT_C void TDbColumn::SetL(TInt64 aValue)
sl@0
    33
	{
sl@0
    34
	*(TInt64*)Row().SetColumnWidthL(iColumn,sizeof(aValue))=aValue;
sl@0
    35
	}
sl@0
    36
sl@0
    37
EXPORT_C void TDbColumn::SetL(TReal32 aValue) __SOFTFP
sl@0
    38
	{
sl@0
    39
	*(TReal32*)Row().SetColumnWidthL(iColumn,sizeof(aValue))=aValue;
sl@0
    40
	}
sl@0
    41
sl@0
    42
EXPORT_C void TDbColumn::SetL(TReal64 aValue) __SOFTFP
sl@0
    43
	{
sl@0
    44
	*(TReal64*)Row().SetColumnWidthL(iColumn,sizeof(aValue))=aValue;
sl@0
    45
	}
sl@0
    46
sl@0
    47
EXPORT_C void TDbColumn::SetL(const TDesC8& aValue)
sl@0
    48
	{
sl@0
    49
	SetL(aValue.Ptr(),aValue.Length());
sl@0
    50
	}
sl@0
    51
sl@0
    52
EXPORT_C void TDbColumn::SetL(const TDesC16& aValue)
sl@0
    53
	{
sl@0
    54
	SetL(aValue.Ptr(),aValue.Length()<<1);
sl@0
    55
	}
sl@0
    56
sl@0
    57
EXPORT_C void TDbColumn::SetBlobL(TDbBlobId aBlobId,TInt aSize)
sl@0
    58
	{
sl@0
    59
	new(Row().SetColumnWidthL(iColumn,TDbBlob::RefSize())) TDbBlob(aBlobId,aSize);
sl@0
    60
	}
sl@0
    61
sl@0
    62
EXPORT_C void TDbColumn::SetBlobL(const TUint8* aData,TInt aSize)
sl@0
    63
	{
sl@0
    64
	new(Row().SetColumnWidthL(iColumn,TDbBlob::InlineSize(aSize))) TDbBlob(aData,aSize);
sl@0
    65
	}
sl@0
    66
sl@0
    67
EXPORT_C TDbBlob& TDbColumn::InitBlobL()
sl@0
    68
	{
sl@0
    69
	return *new(Row().SetColumnWidthL(iColumn,sizeof(TDbBlob))) TDbBlob;
sl@0
    70
	}
sl@0
    71
sl@0
    72
EXPORT_C void TDbColumn::CommitBlob(const TDbBlob& aBlob)
sl@0
    73
	{
sl@0
    74
#if defined(_DEBUG)
sl@0
    75
	TDbColumnC colC(*this);
sl@0
    76
	__ASSERT(&colC.Blob()==&aBlob);
sl@0
    77
	__ASSERT(colC.Size()>=aBlob.CellSize());
sl@0
    78
#endif
sl@0
    79
	TRAPD(errCode, Row().SetColumnWidthL(iColumn,aBlob.Size() ? aBlob.CellSize() : 0));
sl@0
    80
    UNUSED_VAR(errCode);
sl@0
    81
	}
sl@0
    82
sl@0
    83
// The row buffer
sl@0
    84
// Minimum data width is 4 bytes for strict alignment
sl@0
    85
// No integral set members for small integers and extractors do the cast down from 4-byte integers
sl@0
    86
sl@0
    87
EXPORT_C RDbRow::RDbRow()
sl@0
    88
//
sl@0
    89
// default to dynamic-owned empty row buffer
sl@0
    90
//
sl@0
    91
	:iFirst(0),iLast(0),iEnd(0),iCell(0),iColumn(TUint(EOwned))
sl@0
    92
	{}
sl@0
    93
sl@0
    94
EXPORT_C void RDbRow::Open(TAny* aBuf,TInt aSize,TInt aMaxSize)
sl@0
    95
//
sl@0
    96
// Use the provided row buffer
sl@0
    97
//
sl@0
    98
	{
sl@0
    99
	iFirst=(TDbCell*)aBuf;
sl@0
   100
	iEnd=PtrAdd(iFirst,aMaxSize);
sl@0
   101
	iColumn=0;			// non-owned buffer
sl@0
   102
	SetSize(aSize);
sl@0
   103
	}
sl@0
   104
sl@0
   105
EXPORT_C void RDbRow::CreateL(TInt aMaxSize)
sl@0
   106
	{
sl@0
   107
	__ASSERT(!iFirst && Owned());
sl@0
   108
	GrowL(aMaxSize);
sl@0
   109
	}
sl@0
   110
sl@0
   111
void RDbRow::PushL()
sl@0
   112
//
sl@0
   113
// Dynamic reallocation requires that the buffer is pushed
sl@0
   114
//
sl@0
   115
	{
sl@0
   116
	CleanupClosePushL(*this);
sl@0
   117
	}
sl@0
   118
sl@0
   119
EXPORT_C void RDbRow::Close()
sl@0
   120
//
sl@0
   121
// release the buffer if owned, and return to default constructed state
sl@0
   122
//
sl@0
   123
	{
sl@0
   124
	if (Owned())
sl@0
   125
		User::Free(iFirst);
sl@0
   126
	iFirst=iLast=iEnd=iCell=0;
sl@0
   127
	iColumn=TUint(EOwned);
sl@0
   128
	}
sl@0
   129
sl@0
   130
EXPORT_C void RDbRow::SetSize(TInt aSize)
sl@0
   131
//
sl@0
   132
// Set the current buffer size: assert that it is valid
sl@0
   133
//
sl@0
   134
	{
sl@0
   135
	__ASSERT(PtrAdd(iFirst,aSize)<=iEnd);
sl@0
   136
	iLast=PtrAdd(iFirst,aSize);
sl@0
   137
	SetCache(iFirst,0);
sl@0
   138
	}
sl@0
   139
sl@0
   140
EXPORT_C void RDbRow::GrowL(TInt aMaxSize)
sl@0
   141
//
sl@0
   142
// Grow the buffer to at least aMaxSize, the buffer empty on return
sl@0
   143
//
sl@0
   144
	{
sl@0
   145
	if (aMaxSize>MaxSize())
sl@0
   146
		{
sl@0
   147
		ReallocL(aMaxSize);
sl@0
   148
		Reset();
sl@0
   149
	//
sl@0
   150
		__ASSERT(iFirst<=iEnd);
sl@0
   151
		__ASSERT(iFirst<=iLast && iLast<=iEnd);
sl@0
   152
		__ASSERT(iFirst<=iCell && iCell<=iLast);
sl@0
   153
		}
sl@0
   154
	}
sl@0
   155
sl@0
   156
void RDbRow::ExtendL(TInt aAdjust)
sl@0
   157
//
sl@0
   158
// Adjust the buffer length by aAdjust, leave if no room, preserve contents and cache
sl@0
   159
//
sl@0
   160
	{
sl@0
   161
	TDbCell* newLast=PtrAdd(iLast,aAdjust);
sl@0
   162
	if (newLast>iEnd)
sl@0
   163
		{
sl@0
   164
		TInt move=ReallocL(Diff(iFirst,newLast));
sl@0
   165
		iCell=PtrAdd(iCell,move);
sl@0
   166
		newLast=PtrAdd(newLast,move);
sl@0
   167
		}
sl@0
   168
	iLast=newLast;
sl@0
   169
// check invariant
sl@0
   170
	__ASSERT(iFirst<=iEnd);
sl@0
   171
	__ASSERT(iFirst<=iLast && iLast<=iEnd);
sl@0
   172
	__ASSERT(iFirst<=iCell && iCell<=iLast);
sl@0
   173
	}
sl@0
   174
sl@0
   175
TInt RDbRow::ReallocL(TInt aMaxSize)
sl@0
   176
//
sl@0
   177
// Grow the buffer to aMaxSize, return the offset of buffer movement
sl@0
   178
// leave iLast and cache untouched
sl@0
   179
//
sl@0
   180
	{
sl@0
   181
	__ASSERT(aMaxSize>MaxSize());
sl@0
   182
	if (!Owned())
sl@0
   183
		__LEAVE(KErrTooBig);	// cannot reallocate if not owned
sl@0
   184
//
sl@0
   185
	aMaxSize+=EGranularity-1;
sl@0
   186
	aMaxSize&=~(EGranularity-1);
sl@0
   187
	TDbCell* buf=(TDbCell*)User::ReAllocL(iFirst,aMaxSize);
sl@0
   188
	TInt move=Diff(iFirst,buf);
sl@0
   189
	iFirst=buf;
sl@0
   190
	iEnd=PtrAdd(buf,aMaxSize);
sl@0
   191
	return move;
sl@0
   192
	}
sl@0
   193
sl@0
   194
TDbCell* RDbRow::Column(TInt aColIx) const
sl@0
   195
//
sl@0
   196
// aCol is now zero-based
sl@0
   197
// Return a pointer to column aCol in the buffer
sl@0
   198
// Return 0 if the column is past the end
sl@0
   199
//
sl@0
   200
	{
sl@0
   201
	TInt ix=Column();
sl@0
   202
	TDbCell* pC;
sl@0
   203
	if (aColIx<ix)
sl@0
   204
		{
sl@0
   205
		ix=0;
sl@0
   206
		pC=iFirst;
sl@0
   207
		}
sl@0
   208
	else
sl@0
   209
		pC=iCell;
sl@0
   210
	TDbCell* last=iLast;
sl@0
   211
	for (;;)
sl@0
   212
		{
sl@0
   213
		if (pC>=last)
sl@0
   214
			break;
sl@0
   215
		if (ix>=aColIx)
sl@0
   216
			break;
sl@0
   217
		pC=pC->Next();
sl@0
   218
		++ix;
sl@0
   219
		}
sl@0
   220
	CONST_CAST(RDbRow*,this)->SetCache(pC,ix);
sl@0
   221
	return pC<last?pC:0;
sl@0
   222
	}
sl@0
   223
sl@0
   224
LOCAL_C const TDbCell* NullCell()
sl@0
   225
	{
sl@0
   226
	static TUint32 const NullCell[3]={0,0,0};	// 3 zero words represent any "Null" value
sl@0
   227
//
sl@0
   228
	return REINTERPRET_CAST(const TDbCell*,&NullCell[0]);
sl@0
   229
	}
sl@0
   230
sl@0
   231
EXPORT_C const TDbCell* RDbRow::ColCell(TDbColNo aColNo) const
sl@0
   232
	{
sl@0
   233
	__ASSERT(aColNo>0);
sl@0
   234
	const TDbCell* cell=Column(aColNo-1);
sl@0
   235
	return cell && cell->Length() ? cell : NullCell();
sl@0
   236
	}
sl@0
   237
sl@0
   238
EXPORT_C TAny* RDbRow::SetColumnWidthL(TDbColNo aColNo,TInt aWidth)
sl@0
   239
// set the width for column aCol to Width
sl@0
   240
// add extra NULL columns to buffer as required
sl@0
   241
// return pointer to data for that column
sl@0
   242
	{
sl@0
   243
	__ASSERT(aColNo>0);
sl@0
   244
	TDbCell* pC=Column(--aColNo);
sl@0
   245
	if (pC==0)
sl@0
   246
		{		// add extra NULL columns to buffer
sl@0
   247
		if (aWidth==0)
sl@0
   248
			return 0;	// setting to NULL, don't bother padding
sl@0
   249
		TInt cFill=(aColNo-iColumn)*sizeof(TInt);
sl@0
   250
		ExtendL(cFill+TDbCell::Size(aWidth));
sl@0
   251
		pC=iCell;
sl@0
   252
		Mem::FillZ(pC,cFill);
sl@0
   253
		pC=PtrAdd(pC,cFill);		// set cache
sl@0
   254
		SetCache(pC,aColNo);
sl@0
   255
		}
sl@0
   256
	else
sl@0
   257
		{
sl@0
   258
		TInt adjust=TDbCell::Size(aWidth)-pC->Size();	// how much to add
sl@0
   259
		if (adjust!=0)
sl@0
   260
			{
sl@0
   261
			ExtendL(adjust);
sl@0
   262
			pC=iCell;		// may have moved in extension
sl@0
   263
			TDbCell* pNext=pC->Next();
sl@0
   264
			TDbCell* pAdjust=PtrAdd(pNext,adjust);
sl@0
   265
			Mem::Move(pAdjust,pNext,Diff(pAdjust,iLast));
sl@0
   266
			}
sl@0
   267
		}
sl@0
   268
	pC->SetLength(aWidth);
sl@0
   269
	return pC->Data();
sl@0
   270
	}