Fix for bug 2283 (RVCT 4.0 support is missing from PDK 3.0.h)
Have multiple extension sections in the bld.inf, one for each version
of the compiler. The RVCT version building the tools will build the
runtime libraries for its version, but make sure we extract all the other
versions from zip archives. Also add the archive for RVCT4.
// Copyright (c) 1994-2009 Nokia Corporation and/or its subsidiary(-ies).
// All rights reserved.
// This component and the accompanying materials are made available
// under the terms of the License "Eclipse Public License v1.0"
// which accompanies this distribution, and is available
// at the URL "http://www.eclipse.org/legal/epl-v10.html".
//
// Initial Contributors:
// Nokia Corporation - initial contribution.
//
// Contributors:
//
// Description:
// e32test\buffer\t_bseg.cpp
// Overview:
// Test all aspects of the CBufSeg class.
// API Information:
// CBufSeg.
// Details:
// - Create a segmented dynamic buffer of specified size.
// - Test all operations of CBufSeg class and see if methods are implemented --
// including NewL, Reset, Size, InsertL, Delete, Ptr, BackPtr, Read, Write and Compress.
// - Test CBufSeg constructor is as expected.
// - Insert data into the segmented dynamic buffer and verify that InsertL method
// is as expected using the Read and Write methods.
// - Delete all data using Reset method and check size is zero.
// - Test InsertL, Read, Write and Length methods.
// - Test Ptr, Free, Size, Backptr and SetReserveL methods are as expected.
// - Check self consistancy of segment lengths, and check contents of segmented
// buffer using Ptr() and BackPtr().
// - Verify the size of the of the test buffers are correct.
// - Insert data into the buffer, delete some data from the beginning, middle and end
// then check for results as expected.
// - Verify the data in the buffer before and after Compress method is as expected.
// Platforms/Drives/Compatibility:
// All
// Assumptions/Requirement/Pre-requisites:
// Failures and causes:
// Base Port information:
//
//
#include <e32test.h>
class TBufSegLink : public TDblQueLink
{
public:
inline TBufSegLink() : iLen(0) {}
inline TBufSegLink* Next() const {return((TBufSegLink*)iNext);}
inline TBufSegLink* Prev() const {return((TBufSegLink*)iPrev);}
public:
TInt iLen;
};
class TestCBufSeg
{
public:
TestCBufSeg() : iDummy(0) {};
void Test1(); // Test all operations of the class.
void Test2(); // Inherited Methods
void Test3(); // Insert
void Test4(); // Delete
void Test5(); // Compress
void Test6L(); // borderlines
protected:
TInt iDummy;
static const TInt SegLen;
void CheckSeg(const CBufSeg*);
void CheckContents1(CBufSeg* const);
void CheckContents2(CBufSeg* const);
};
const TInt TestCBufSeg::SegLen=64;
LOCAL_D RTest test(_L("T_BSEG"));
class CSpy : public CBufBase
{
public:
~CSpy();
protected:
CSpy(TInt anExpandSize);
public:
TDblQue<TBufSegLink> iQue;
TBufSegLink* iSeg;
TInt iBase;
TInt iOffset;
};
GLDEF_C void TestCBufSeg::CheckSeg(const CBufSeg* bf)
//
// Check Self consistancy of segment lengths
//
{
if (bf->Size()==0)
return;
TInt sum=0;
TBufSegLink* p1=((CSpy*)bf)->iQue.First();
while (!((CSpy*)bf)->iQue.IsHead(p1))
{
test(p1->iLen<=bf->Size());
sum+=p1->iLen;
p1=p1->Next();
}
test(sum==bf->Size());
sum=0;
p1=((CSpy*)bf)->iQue.Last();
while (!((CSpy*)bf)->iQue.IsHead(p1))
{
test(p1->iLen<=bf->Size());
sum+=p1->iLen;
p1=p1->Prev();
}
test(sum==bf->Size());
}
GLDEF_C void TestCBufSeg::CheckContents1(CBufSeg* const bf)
//
// Check contents of segmented buffer using Ptr()
//
{
TInt sum=0;
TInt nbytes=bf->Size();
for (TInt pos=0;pos<nbytes;)
{
TPtr8 p=bf->Ptr(pos);
TInt len=p.Length();
TInt8* pT=(TInt8*)p.Ptr();
for (TInt i=0;i<len;i++)
sum+=*pT++;
test(sum==0);
pos+=len;
}
}
GLDEF_C void TestCBufSeg::CheckContents2(CBufSeg* const bf)
//
// Check contents of segmented buffer using BackPtr()
//
{
TInt sum=0;
TInt nbytes=bf->Size();
for(TInt pos=nbytes;pos>0;)
{
TPtr8 p=bf->BackPtr(pos);
TInt len=p.Length();
TInt8* pT=(TInt8*)p.Ptr();
for (TInt i=0;i<len;i++)
sum+=*pT++;
pos-=len;
}
test(sum==0);
}
GLDEF_C void TestCBufSeg::Test1()
//
// Test all operations of BufSeg class
//
{
test.Start(_L("Test all operations of CBufSeg"));
CBufSeg* bf=(CBufSeg*)CBufSeg::NewL(100);
bf->Reset();
bf->Size();
bf->InsertL(0,TPtrC8((TText8*)"Hello World"));
bf->Delete(0,5);
TText8* tp=(TText8*)bf->Ptr(3).Ptr();
tp=(TText8*)bf->BackPtr(3).Ptr();
TBuf8<0x20> txt;
bf->Read(2,txt,2);
bf->Write(2,txt,2);
bf->Compress();
delete bf;
test.End();
}
GLDEF_C void TestCBufSeg::Test2()
//
// Test all inherited methods
//
{
TBuf8<0x40> tb1=(TText8*)"Hello World";
TBuf8<0x40> tb2=(TText8*)"String number two";
TBuf8<0x40> tb3;
test.Start(_L("Free,Size,Read,Write,Reset"));
CBufSeg* bf=(CBufSeg*)CBufSeg::NewL(SegLen);
test(bf->Size()==0);
bf->InsertL(0,tb1);
test(bf->Size()==tb1.Length());
bf->Read(6,tb3,5);
test(tb3==tb1.Right(5));
bf->Write(1,tb2,6);
bf->Read(0,tb3,bf->Size());
test(tb3==TPtrC8((TText8*)"HStringorld"));
bf->Reset();
test(bf->Size()==0);
while (bf->Size()<400)
{
bf->InsertL(bf->Size(),tb1);
bf->InsertL(bf->Size(),tb2);
}
TInt i=0;
while (i<400)
{
bf->Read(i,tb3,tb1.Size());
test(tb3==tb1);
i+=tb1.Length();
bf->Read(i,tb3,tb2.Size());
test(tb3==tb2);
i+=tb2.Length();
}
i=0;
while (i<400)
{
bf->Write(i,tb2);
i+=tb2.Length();
bf->Write(i,tb1);
i+=tb1.Length();
}
i=0;
while (i<400)
{
bf->Read(i,tb3,tb2.Size());
test(tb3==tb2);
i+=tb2.Length();
bf->Read(i,tb3,tb1.Size());
test(tb3==tb1);
i+=tb1.Length();
}
delete bf;
test.End();
}
GLDEF_C void TestCBufSeg::Test3()
//
// Test input methods
//
{
TInt8 bb[1000];
TInt nbytes;
test.Start(_L("InsertL"));
CBufSeg* bf1=(CBufSeg*)CBufSeg::NewL(SegLen);
CBufSeg* bf2=(CBufSeg*)CBufSeg::NewL(SegLen);
CBufSeg* bf3=(CBufSeg*)CBufSeg::NewL(SegLen);
nbytes=0;
TInt k;
for(TInt j=0;j<20;j++)
{
for(TInt i=0;i<10*j;i+=2)
{
k=i%128;
bb[i]=(TInt8)k;
bb[i+1]=(TInt8)-k;
}
bf1->InsertL(bf1->Size()/3*2,&bb[0],10*j);
CheckSeg(bf1);
CheckContents1(bf1);
CheckContents2(bf1);
bf2->InsertL(bf2->Size(),&bb[0],10*j);
CheckSeg(bf2);
CheckContents1(bf2);
CheckContents2(bf2);
bf3->InsertL(0,&bb[0],10*j);
CheckSeg(bf3);
CheckContents1(bf3);
CheckContents2(bf3);
nbytes+=10*j;
}
test(nbytes==bf1->Size());
test(nbytes==bf2->Size());
test(nbytes==bf3->Size());
delete bf1;
delete bf2;
delete bf3;
test.End();
}
GLDEF_C void TestCBufSeg::Test4()
//
// Delete
//
{
TInt8 bb[1000];
test.Start(_L("Delete"));
CBufSeg* bf1=(CBufSeg*)CBufSeg::NewL(SegLen);
CBufSeg* bf2=(CBufSeg*)CBufSeg::NewL(SegLen);
CBufSeg* bf3=(CBufSeg*)CBufSeg::NewL(SegLen);
TInt nbytes=0;
TInt k;
for(TInt j=0;j<20;j++)
{
for(TInt i=0;i<10*j;i+=2)
{
k=i%128;
bb[i]=(TInt8)k;
bb[i+1]=(TInt8)-k;
}
bf1->InsertL(bf1->Size()/3*2,&bb[0],10*j);
bf2->InsertL(bf2->Size(),&bb[0],10*j);
bf3->InsertL(0,&bb[0],10*j);
nbytes+=10*j;
}
TInt len=34;
TInt aLength;
while (nbytes>len)
{
for (TInt pos=0;pos<nbytes;pos+=44)
{
len=((len+17)%23)*2;
if (len>nbytes-pos)
len=nbytes-pos;
bf1->Delete(pos,len);
CheckSeg(bf1);
CheckContents1(bf1);
CheckContents2(bf1);
aLength=bf2->Ptr(0).Length();
aLength=((aLength>len) ? aLength : len);
bf2->Delete(aLength-len,len);
CheckSeg(bf2);
CheckContents1(bf2);
CheckContents2(bf2);
bf3->Delete(0,len);
CheckSeg(bf3);
CheckContents1(bf3);
CheckContents2(bf3);
nbytes-=len;
test(nbytes==bf1->Size());
test(nbytes==bf2->Size());
test(nbytes==bf3->Size());
}
}
delete bf1;
delete bf2;
delete bf3;
test.End();
}
GLDEF_C void TestCBufSeg::Test5()
//
// Compress
//
{
TInt8 bb[1000];
test.Start(_L("Compress"));
CBufSeg* bf1=(CBufSeg*)CBufSeg::NewL(SegLen);
CBufSeg* bf2=(CBufSeg*)CBufSeg::NewL(SegLen);
CBufSeg* bf3=(CBufSeg*)CBufSeg::NewL(SegLen);
TInt nbytes=0;
TInt k;
for(TInt j=0;j<20;j++)
{
for(TInt i=0;i<10*j;i+=2)
{
k=i%128;
bb[i]=(TInt8)k;
bb[i+1]=(TInt8)-k;
}
bf1->InsertL(bf1->Size()/3*2,&bb[0],10*j);
bf2->InsertL(bf2->Size(),&bb[0],10*j);
bf3->InsertL(0,&bb[0],10*j);
nbytes+=10*j;
}
TInt len=34;
TInt aLength;
while (nbytes>len)
{
for (TInt pos=0;pos<nbytes;pos+=44)
{
if (len>nbytes-pos)
len=nbytes-pos;
bf1->Delete(pos,len);
bf1->Compress();
CheckSeg(bf1);
CheckContents1(bf1);
CheckContents2(bf1);
aLength=bf2->Ptr(0).Length();
aLength=((aLength>len)? aLength : len);
bf2->Delete(aLength-len,len);
bf2->Compress();
CheckSeg(bf2);
CheckContents1(bf2);
CheckContents2(bf2);
bf3->Delete(0,len);
bf3->Compress();
CheckSeg(bf3);
CheckContents1(bf3);
CheckContents2(bf3);
nbytes-=len;
test(nbytes==bf1->Size());
test(nbytes==bf2->Size());
test(nbytes==bf3->Size());
}
}
delete bf1;
delete bf2;
delete bf3;
test.End();
}
void TestCBufSeg::Test6L()
{
test.Start(_L("Test compress frees empty cells"));
__UHEAP_MARK;
TUint8 alphabet[27] = "abcdefghijklmnopqrstuvwxyz";
CBufSeg* buf = CBufSeg::NewL(10);
CleanupStack::PushL(buf);
buf->InsertL(0, alphabet, 16); // "abcdefghij" ++ "klmnop"
buf->Delete(5, 5); // "abcde" ++ "klmnop"
buf->Delete(10, 1); // "abcde" ++ "klmno"
buf->Compress(); // "abcdefklmno". i.e. empty cell should be freed.
CleanupStack::PopAndDestroy(buf);
__UHEAP_MARKEND;
test.End();
}
LOCAL_C void test_CBufSeg()
//
// Test the BufSeg class
//
{
TestCBufSeg b;
test.Start(_L("All operations"));
b.Test1();
test.Next(_L("Inherited Methods"));
b.Test2();
test.Next(_L("Insert"));
b.Test3();
test.Next(_L("Delete"));
b.Test4();
test.Next(_L("Compress"));
b.Test5();
test.Next(_L("Bordeline cases"));
TRAPD(r,b.Test6L());
test(r==KErrNone);
//
test.End();
}
GLDEF_C TInt E32Main()
//
// Test the ADT segmented varray.
//
{
test.Title();
__UHEAP_MARK;
//
// Install a trap handler
//
CTrapCleanup* trapHandler=CTrapCleanup::New();
test(trapHandler!=NULL);
// CleanupStack::NextLevel();
test.Start(_L("class CBufSeg"));
test_CBufSeg();
delete trapHandler;
__UHEAP_MARKEND;
test.End();
return(0);
}