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) 2006-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:
// f32test\demandpaging\t_clamp.cpp
// Test suite for file clamping, file clamping is used to prevent files
// (exes or dlls) from being deleted whilst in use.
// 002 GetDriveLetters()
// 003 Test1() Basic clamp operation
// 004 Test2() Invalid clamp requests
// 005 Test3() Denied FS requests when file(s) are clamped
// 006 Test3Operations() Test other RFile, RFs operations
// 007 Test3Operations() Increase number of clamps to MY_N
// 008 Test3Operations() Decrease number of clamps by MY_M
// 009 Test3Operations() Increase number of clamps by MY_M
// 010 TestDeferredDismount() Open and clamp file, register for dismount
// notification, then issue dismount instruction.
// 011 Test4() Clamp tests for non-writable file system
// 012 Test5() Clamp requests on non-clamping file systems
//
//
//! @SYMTestCaseID KBASE-T_CLAMP-0328
//! @SYMTestType UT
//! @SYMPREQ PREQ1110
//! @SYMTestCaseDesc Demand Paging File Clamp tests
//! @SYMTestActions 001 Starting T_CLAMP
//! @SYMTestExpectedResults All tests should pass.
//! @SYMTestPriority High
//! @SYMTestStatus Implemented
#define __E32TEST_EXTENSION__
#include <e32test.h>
RTest test(_L("T_CLAMP"));
#if defined(_DEBUG) || defined(_DEBUG_RELEASE)
#include <f32file.h>
#include <f32dbg.h>
#include <e32ldr_private.h>
RFs TheFs;
_LIT(KFATName,"FAT");
//_LIT(KFAT32Name,"FAT32");
_LIT(KROFSName,"ROFS");
_LIT(KLFFSName,"LFFS");
_LIT(KCOMPName,"COMPOSITE"); // Z: name if Composite File System
//#ifdef __WINS__
//_LIT(KROMName,"WIN32"); // Clamping is not supported for non-composite filing system on Z:
//#else
_LIT(KROMName,"ROM"); // Z: name if ROMFS (on hardware, not emulator)
//#endif
TChar NandFatDrv='?';
TChar RofsDrv='?';
TChar LffsDrv='?';
TChar CompDrv='?';
LOCAL_C void Test1()
{
// Basic clamp operation
test.Next(_L("T_Clamp - Test1()"));
TBuf<256> fileName;
TBuf<256> buf(_L("buffer for file used"));
fileName = _L("clampFile.tst");
RFile testFile;
TInt r=testFile.Replace(TheFs,fileName,EFileWrite);
test(r==KErrNone);
TPtrC8 pBuf((TUint8*)&buf);
testFile.Write(pBuf);
testFile.Flush();
// Clamp file
RFileClamp handle;
r=handle.Clamp(testFile);
test(r==KErrNone);
TInt64 storedCookie_0=handle.iCookie[0];
TInt64 storedCookie_1=handle.iCookie[1];
// Try to clamp previously-clamped file
RFileClamp handle1;
r=handle1.Clamp(testFile);
test(r==KErrNone);
// Unclamp file
r=handle.Close(TheFs);
test (r==KErrNone);
// Check cookie content has been re-initialised
test((0==handle.iCookie[0])&&(0==handle.iCookie[1]));
// Try to unclamp a file that is not clamped
handle.iCookie[0]=storedCookie_0;
handle.iCookie[1]=storedCookie_1;
r=handle.Close(TheFs);
test (r==KErrNotFound);
// Check that attempting to unclamp with a zero-content cookie
// yields no error
handle.iCookie[0]=0;
handle.iCookie[1]=0;
r=handle.Close(TheFs);
test (r==KErrNone);
// Clamp the file (again)
r=handle.Clamp(testFile);
test(r==KErrNone);
// Create and clamp a second file ...
fileName = _L("clampFile2.tst");
RFile testFile2;
r=testFile2.Replace(TheFs,fileName,EFileWrite);
test(r==KErrNone);
buf=_L("buffer for file 2");
testFile2.Write(pBuf);
testFile2.Flush();
RFileClamp handle2;
r=handle2.Clamp(testFile2);
test(r==KErrNone);
// Create and clamp a third file ...
RFileClamp handle3;
fileName = _L("clampFile3.tst");
RFile testFile3;
r=testFile3.Replace(TheFs,fileName,EFileWrite);
test(r==KErrNone);
buf=_L("buffer for file 3");
testFile3.Write(pBuf);
testFile3.Flush();
r=handle3.Clamp(testFile3);
test(r==KErrNone);
// Test can unclamp then reclamp first file
// then repeat for the third file
r=handle.Close(TheFs);
test (r==KErrNone);
r=handle.Clamp(testFile);
test(r==KErrNone);
r=handle3.Close(TheFs);
test (r==KErrNone);
r=handle3.Clamp(testFile3);
test(r==KErrNone);
// Tidy up
r=handle.Close(TheFs);
test (r==KErrNone);
r=handle1.Close(TheFs);
test (r==KErrNone);
testFile.Close();
r=TheFs.Delete(_L("clampFile.tst"));
test (r==KErrNone);
r=handle2.Close(TheFs);
test (r==KErrNone);
testFile2.Close();
r=TheFs.Delete(_L("clampFile2.tst"));
test (r==KErrNone);
r=handle3.Close(TheFs);
test (r==KErrNone);
testFile3.Close();
r=TheFs.Delete(_L("clampFile3.tst"));
test (r==KErrNone);
}
LOCAL_C void Test2()
{
// Invalid clamp requests
test.Next(_L("T_Clamp - Test2()"));
// Test attempt to clamp empty file is rejected
RFileClamp handle4;
TBuf<256> file4Name;
file4Name = _L("clampFile4.tst");
RFile testFile4;
TInt r=testFile4.Replace(TheFs,file4Name,EFileWrite);
test(r==KErrNone);
r=handle4.Clamp(testFile4);
test(r==KErrEof);
// Preparation for next test - create a valid clamp handle
TBuf<256> buf4(_L("buffer for file 4"));
TPtrC8 pBuf4((TUint8*)&buf4);
testFile4.Write(pBuf4);
testFile4.Flush();
r=handle4.Clamp(testFile4);
test(r==KErrNone);
// Try to unclamp non-existant file
RFileClamp handle5;
memcpy((TAny*)&handle5,(TAny*)&handle4,sizeof(RFileClamp));
handle5.iCookie[0] = MAKE_TINT64(-1,-1); // iCookie[0] holds the unique ID
r=handle5.Close(TheFs);
test (r==KErrNotFound);
// Tidy up
r=handle4.Close(TheFs);
test (r==KErrNone);
testFile4.Close();
r=TheFs.Delete(_L("clampFile4.tst"));
test (r==KErrNone);
}
LOCAL_C void TestDeferredDismount(TDesC& aRoot, TDesC& aFileName, RFileClamp* handlePtr)
{
// Open and clamp file, register for dismount notification, then issue
// dismount instruction.
// Since there are no other clients registered for dismount notification,
// this would normally lead too dismount being instigated. However, since
// the file is clamped, dismount should be deferred
test.Next(_L("T_Clamp - TestDeferredDismount()"));
// File system details required for clean-up
const TInt KMaxFileSystemNameLength=100; // Arbitrary length
const TInt KMaxFileSystemExtNameLength=100; // Arbitrary length
TBuf<KMaxFileSystemNameLength> fsName;
TBuf<KMaxFileSystemExtNameLength> fsExtName_0;
TBuf<KMaxFileSystemExtNameLength> fsExtName_1;
TBool fsExt0Present=EFalse;
TBool fsExt1Present=EFalse;
TInt driveNo, r;
r=TheFs.CharToDrive(aRoot[0], driveNo);
test(r==KErrNone);
r=TheFs.FileSystemName(fsName, driveNo);
test(r==KErrNone);
r=TheFs.ExtensionName(fsExtName_0,driveNo,0);
if(r==KErrNone)
fsExt0Present=ETrue;
r=TheFs.ExtensionName(fsExtName_1,driveNo,1);
if(r==KErrNone)
fsExt1Present=ETrue;
// Create a file & write to it so that we can test whether dismounting works correctly with dirty data
TDriveInfo driveInfo;
test(TheFs.Drive(driveInfo, driveNo) == KErrNone);
TFileName dirtyFileName(_L("dirtyFile.tst"));
RFile dirtyFile;
if (!(driveInfo.iMediaAtt & KMediaAttWriteProtected))
{
r=dirtyFile.Replace(TheFs, dirtyFileName, EFileWrite);
test(r==KErrNone);
r=dirtyFile.Write(_L8("My name is Michael Caine"));
test(r==KErrNone);
}
RFile testFile;
r=testFile.Open(TheFs,aFileName,EFileRead);
test(r==KErrNone);
r=handlePtr->Clamp(testFile);
test(r==KErrNone);
testFile.Close();
TRequestStatus clientNotify=KErrNone;
TRequestStatus clientDismount=KErrNone;
TheFs.NotifyDismount(driveNo, clientNotify); // Register for notification
test(clientNotify == KRequestPending);
TheFs.NotifyDismount(driveNo, clientDismount, EFsDismountNotifyClients);
test(clientDismount == KRequestPending);
User::WaitForRequest(clientNotify);
test(clientNotify == KErrNone);
r=TheFs.AllowDismount(driveNo); // Respond to dismount notification
test(r == KErrNone);
test(clientDismount == KRequestPending); // Dismount is deferred
//
// Now unclamp the file, and check that the deferred dismount is performed.
r=handlePtr->Close(TheFs);
test(r==KErrNone);
User::WaitForRequest(clientDismount);
test(clientDismount == KErrNone);
// Try to write to the opened file: this should return KErrNotReady as there is no drive thread
if (!(driveInfo.iMediaAtt & KMediaAttWriteProtected))
{
r=dirtyFile.Write(_L8("My name isn't really Michael Caine"));
test(r==KErrNotReady);
}
// Re-mount the file system
if(fsExt0Present)
{
r=TheFs.MountFileSystem(fsName,fsExtName_0,driveNo);
test(r==KErrNone);
}
else if(fsExt1Present) // untested !
{
r=TheFs.MountFileSystem(fsName,fsExtName_1,driveNo);
test(r==KErrNone);
}
else
{
r=TheFs.MountFileSystem(fsName,driveNo);
test_KErrNone(r);
}
// create some more dirty data to verify that the file server can cope with the drive thread
// having gone & come back again
if (!(driveInfo.iMediaAtt & KMediaAttWriteProtected))
{
r=dirtyFile.Write(_L8("My name is Michael Phelps and I'm a fish."));
test(r==KErrDisMounted);
dirtyFile.Close();
r = TheFs.Delete(dirtyFileName);
test(r == KErrNone);
}
// Issue a EFsDismountNotifyClients with no clients but with files clamped
// & verify that the dismount request completes when clamps are removed
r=testFile.Open(TheFs,aFileName,EFileRead);
test(r==KErrNone);
r=handlePtr->Clamp(testFile);
test(r==KErrNone);
testFile.Close();
TheFs.NotifyDismount(driveNo, clientDismount, EFsDismountNotifyClients);
test(clientDismount == KRequestPending);
r=handlePtr->Close(TheFs);
test(r==KErrNone);
User::WaitForRequest(clientDismount);
test(clientDismount == KErrNone);
// Re-mount the file system again
if(fsExt0Present)
{
r=TheFs.MountFileSystem(fsName,fsExtName_0,driveNo);
test(r==KErrNone);
}
else if(fsExt1Present) // untested !
{
r=TheFs.MountFileSystem(fsName,fsExtName_1,driveNo);
test(r==KErrNone);
}
else
{
r=TheFs.MountFileSystem(fsName,driveNo);
test_KErrNone(r);
}
// Issue a EFsDismountForceDismount with no clients but with files clamped
// & verify that the dismount request completes when clamps are removed
r=testFile.Open(TheFs,aFileName,EFileRead);
test(r==KErrNone);
r=handlePtr->Clamp(testFile);
test(r==KErrNone);
testFile.Close();
TheFs.NotifyDismount(driveNo, clientDismount, EFsDismountForceDismount);
test(clientDismount == KRequestPending);
r=handlePtr->Close(TheFs);
test(r==KErrNone);
User::WaitForRequest(clientDismount);
test(clientDismount == KErrNone);
// Re-mount the file system again
if(fsExt0Present)
{
r=TheFs.MountFileSystem(fsName,fsExtName_0,driveNo);
test(r==KErrNone);
}
else if(fsExt1Present) // untested !
{
r=TheFs.MountFileSystem(fsName,fsExtName_1,driveNo);
test(r==KErrNone);
}
else
{
r=TheFs.MountFileSystem(fsName,driveNo);
test_KErrNone(r);
}
}
LOCAL_C void Test3Operations(TDesC& aRoot, TDesC& aFileName)
{
test.Next(_L("T_Clamp - Test3Operations()"));
// RFormat::Open
#ifdef __WINS__
if (User::UpperCase(aRoot[0]) != 'C')
#endif
{
TBuf<4> driveBuf=_L("?:\\");
driveBuf[0] = aRoot[0];
RFormat format;
TInt count;
TInt r=format.Open(TheFs,driveBuf,EFullFormat,count);
test(r==KErrInUse);
format.Close();
}
// Dismount: synchronous requests
// RFs::DismountFileSystem, RFs::SwapFileSystem
const TInt KMaxFileSystemNameLength=100; // Arbitrary length
TBuf<KMaxFileSystemNameLength> fileSysName;
TInt driveNo, r;
r=TheFs.CharToDrive(aRoot[0], driveNo);
test(r==KErrNone);
r=TheFs.FileSystemName(fileSysName,driveNo);
test(r==KErrNone);
r=TheFs.DismountFileSystem(fileSysName,driveNo);
test(r==KErrInUse);
r=TheFs.SwapFileSystem(fileSysName,fileSysName,driveNo);
test(r==KErrInUse);
#if defined(_DEBUG) || defined(_DEBUG_RELEASE)
// The cancellation of deferred dismounts requires controlIO
// functionality available in debug versions of the code.
// Dismount: asynchronous requests
// RFs::NotifyDismount, RFs::AllowDismount
const TInt KNumClients = 5;
RFs clientFs[KNumClients];
TRequestStatus clientNotify[KNumClients];
TRequestStatus clientComplete;
TInt i=0;
for(i=0; i< KNumClients; i++)
{
r=clientFs[i].Connect();
test(r==KErrNone);
}
// Cancel any deferred dismount in preparation for the next test
r=TheFs.ControlIo(driveNo,KControlIoCancelDeferredDismount);
test(r==KErrNone);
// Use case 1: Orderly dismount
// All clients register for dismount notification
for(i=0; i< KNumClients; i++)
{
clientNotify[i] = KErrNone;
clientFs[i].NotifyDismount(driveNo, clientNotify[i]);
test(clientNotify[i] == KRequestPending);
}
// First client notifies intent to dismount
clientComplete = KErrNone;
clientFs[0].NotifyDismount(driveNo, clientComplete, EFsDismountNotifyClients);
test(clientComplete == KRequestPending);
// Check all clients have received the notification
for(i=0; i< KNumClients; i++)
{
test(clientNotify[i] == KErrNone);
}
// All clients invoke AllowDismount
for(i=0; i< KNumClients; i++)
{
r=clientFs[i].AllowDismount(driveNo);
test(r==KErrNone);
}
// Dismount is deferred
test(clientComplete == KRequestPending);
// Cancel the deferred dismount in preparation for the next test
clientFs[0].NotifyDismountCancel(clientComplete);
test(clientComplete == KErrCancel);
r=TheFs.ControlIo(driveNo,KControlIoCancelDeferredDismount);
test(r==KErrNone);
clientComplete=KErrNone; // Re-initialise the TRequestStatus
// Use case 2: Forced dismount
// All clients register for dismount notification
for(i=0; i< KNumClients; i++)
{
clientFs[i].NotifyDismount(driveNo, clientNotify[i]);
test(clientNotify[i] == KRequestPending);
}
// First client notifies intent to dismount
clientFs[0].NotifyDismount(driveNo, clientComplete, EFsDismountNotifyClients);
test(clientComplete == KRequestPending);
// Check all clients have received the notification
for(i=0; i< KNumClients; i++)
{
test(clientNotify[i] == KErrNone);
}
// Not all other clients invoke AllowDismount
for(i=0; i< KNumClients-1; i++)
{
clientFs[i].AllowDismount(driveNo);
}
// First client attempts forced dismount
test(clientComplete == KRequestPending);
clientFs[0].NotifyDismount(driveNo, clientComplete, EFsDismountForceDismount);
// Dismount is deferred
test(clientComplete == KRequestPending);
// Cancel the deferred dismount in preparation for the next test
// Also cancel the 'un-Allowed' notification request
clientFs[0].NotifyDismountCancel(clientComplete);
test(clientComplete == KErrCancel);
r=TheFs.ControlIo(driveNo,KControlIoCancelDeferredDismount);
test(r==KErrNone);
clientComplete=KErrNone; // Re-initialise the TRequestStatus
#endif
// RFile::Open with EFileWrite
RFile testFile;
r=testFile.Open(TheFs,aFileName,EFileWrite|EFileShareReadersOrWriters);
test(r==KErrInUse);
// RFile::Replace
RFile testFile2;
r=testFile2.Replace(TheFs,aFileName,EFileRead);
test(r==KErrInUse);
testFile2.Close();
// RFile::Set - this should not be prevented by clamping
r=testFile.Open(TheFs,aFileName,EFileRead|EFileShareAny);
test(r == KErrNone);
TTime origTime;
TUint origAtt;
r=testFile.Att(origAtt);
test(r==KErrNone);
r=testFile.Modified(origTime);
test(r==KErrNone);
TTime time; // Arbitrary value
TUint setMask=0xA5A5&~KEntryAttReadOnly; // Not read-only, otherwise arbitrary value
TUint clearMask=0x5A5A & KEntryAttReadOnly; // Not read-only, otherwise arbitrary value
r=testFile.Set(time,setMask,clearMask);
test(r==KErrNone);
r=testFile.Set(origTime,origAtt,~origAtt); // restore original values
test(r==KErrNone);
testFile.Close();
// RFs::Rename - this should not be prevented by clamping
r=TheFs.Rename(aFileName,_L("aDummyName"));
test(r==KErrNone);
r=TheFs.Rename(_L("aDummyName"),aFileName); // restore original name
test(r==KErrNone);
// RFs::Replace
r=TheFs.Replace(aFileName,_L("aDummyName"));
test(r==KErrInUse);
// RFs::SetEntry - this should not be prevented by clamping
r=TheFs.SetEntry(aFileName,time,setMask,clearMask);
test(r==KErrNone);
r=TheFs.SetEntry(aFileName,origTime,origAtt,~origAtt); // restore original values
test(r==KErrNone);
// RFs::Delete
r=TheFs.Delete(aFileName);
test(r==KErrInUse);
// RRawDisk::Open (*** no longer required ***)
}
LOCAL_C void Test3(TDesC& aRoot)
{
// Denied FS requests when file(s) are clamped.
test.Next(_L("T_Clamp - Test3()"));
// Clamping is reference counted, so we need a test to check that
// a file clamped N times cannot be modified until it has been unclamped N times.
// Should also check
// - Clamp N times
// - Unclamp M times (M<N)
// - Clamp M times.
// - Unclamp N times
#define MY_N 16
#define MY_M 12
// Create a file for use
TBuf<256> fileName;
TBuf<256> buf(_L("buffer for file used"));
fileName = _L("clampFile.tst");
RFile testFile;
TInt r=testFile.Replace(TheFs,fileName,EFileWrite);
test(r==KErrNone);
TPtrC8 pBuf((TUint8*)&buf);
testFile.Write(pBuf);
testFile.Flush();
// Close file,then re-open (to support clamping) in sharable mode
// (to allow testing of RFile::Open with EFileWrite)
testFile.Close();
r=testFile.Open(TheFs,fileName,EFileWrite|EFileShareReadersOrWriters);
test(r==KErrNone);
// Show, prior to clamping, that the file can be opened with EFileWrite
RFile testFile2;
r=testFile2.Open(TheFs,fileName,EFileWrite|EFileShareReadersOrWriters);
test(r==KErrNone);
// Close the second RFile instance
testFile2.Close();
// Clamp and unclamp a number of times, and invoke the
// operations to test
RFileClamp myHandles[MY_N];
RFileClamp *handlePtr = myHandles;
TInt i = 0;
// Clamp once
r=handlePtr->Clamp(testFile);
test(r==KErrNone);
i++;
// RFile::SetAtt - this should not be prevented by clamping
TTime origTime;
TUint origAtt;
r=testFile.Att(origAtt);
test(r==KErrNone);
r=testFile.Modified(origTime);
test(r==KErrNone);
TTime time; // Arbitrary value
TUint setMask=0xA5A5&~KEntryAttReadOnly; // Not read-only, otherwise arbitrary value
TUint clearMask=0x5A5A & KEntryAttReadOnly; // Not read-only, otherwise arbitrary value
r=testFile.Att(origAtt);
test(r==KErrNone);
r=testFile.SetAtt(setMask,clearMask);
test(r==KErrNone);
r=testFile.Set(origTime,origAtt,~origAtt); // restore original values
test(r==KErrNone);
// RFile::SetModified - this should not be prevented by clamping
r=testFile.Modified(origTime);
test(r==KErrNone);
r=testFile.SetModified(time);
test(r==KErrNone);
r=testFile.SetModified(origTime); // restore original value
test(r==KErrNone);
// RFile::Rename - this should not be prevented by clamping
// Need file to be opened in EFileShareExclusive sharing mode,
// so close, unclamp, re-open appropriately and re-clamp
testFile.Close();
r=handlePtr->Close(TheFs);
test(r==KErrNone);
i--;
r=testFile.Open(TheFs,fileName,EFileWrite|EFileShareExclusive);
test(r==KErrNone);
r=handlePtr->Clamp(testFile);
test(r==KErrNone);
i++;
r=testFile.Rename(_L("aDummyName"));
test(r==KErrNone);
r=testFile.Rename(fileName);
test(r==KErrNone);
// RFile::SetSize
r=testFile.SetSize(1000); // Arbitrary value
test(r==KErrInUse);
// Test other RFile, RFs operations
testFile.Close();
Test3Operations(aRoot,fileName);
// Increase number of clamps to MY_N
r=testFile.Open(TheFs,fileName,EFileRead);
test(r==KErrNone);
for(; i < MY_N; i++)
{
handlePtr++;
r=handlePtr->Clamp(testFile);
test(r==KErrNone);
}
testFile.Close();
Test3Operations(aRoot,fileName);
// Decrease number of clamps by MY_M
for(;i > (MY_N - MY_M); i--)
{
r=handlePtr->Close(TheFs);
test(r==KErrNone);
if(handlePtr!=myHandles)
handlePtr--;
else
break;
}
Test3Operations(aRoot,fileName);
// Increase number of clamps by MY_M
r=testFile.Open(TheFs,fileName,EFileRead);
test(r == KErrNone);
TInt j=0;
for(;j < MY_M; j++)
{
handlePtr++;
r=handlePtr->Clamp(testFile);
test(r==KErrNone);
i++;
}
testFile.Close();
Test3Operations(aRoot,fileName);
// Decrease number of clamps by MY_N
for(;i > 0; i--)
{
r=handlePtr->Close(TheFs);
test(r==KErrNone);
if(handlePtr!=myHandles)
handlePtr--;
else
break;
}
// Test deferred dismount - use next free handle
TestDeferredDismount(aRoot,fileName,handlePtr);
// Re-create the test directory
r=TheFs.MkDirAll(aRoot);
test(r==KErrNone || r== KErrAlreadyExists);
TheFs.SetSessionPath(aRoot);
// No clamps remain - prove RFile::Open with EFileWrite
r=testFile2.Open(TheFs,fileName,EFileWrite|EFileShareReadersOrWriters);
test(r==KErrNone);
testFile2.Close();
// No clamps remain - prove that file can now be deleted
r=TheFs.Delete(_L("clampFile.tst"));
test (r==KErrNone);
}
LOCAL_C void Test4(TDesC& aRoot)
{
// Clamp tests for non-writable file system
test.Next(_L("T_Clamp - Test4()"));
// Tests are limited to clamp, unclamp and denied requests
// when clamps are present.
TBuf<256> pathName;
#ifdef __WINS__
if((aRoot[0]=='Z')||(aRoot[0]=='z'))
pathName=_L("clean.txt");
else
pathName=_L("root.txt");
#else
if((aRoot[0]=='Z')||(aRoot[0]=='z'))
pathName=_L("UnicodeData.txt");
else
pathName=_L("\\Test\\clamp.txt"); // For (non-composite) ROFS drive
#endif
RFile testFile;
TInt r=testFile.Open(TheFs, pathName, EFileRead);
test(r==KErrNone);
// Clamp file
RFileClamp handle;
r=handle.Clamp(testFile);
test(r==KErrNone);
TInt64 storedCookie_0=handle.iCookie[0];
TInt64 storedCookie_1=handle.iCookie[1];
// Try to clamp previously-clamped file
RFileClamp handle1;
r=handle1.Clamp(testFile);
test(r==KErrNone);
// Unclamp file
r=handle.Close(TheFs);
test (r==KErrNone);
// Check cookie content has been re-initialised
test((0==handle.iCookie[0])&&(0==handle.iCookie[1]));
// Try to unclamp a file that is not clamped
handle.iCookie[0]=storedCookie_0;
handle.iCookie[1]=storedCookie_1;
r=handle.Close(TheFs);
test (r==KErrNotFound);
// Remove remaining clamp
r=handle1.Close(TheFs);
test (r==KErrNone);
testFile.Close();
if((aRoot[0]!='Z')&&(aRoot[0]!='z')) // Can not dismount Z:
TestDeferredDismount(aRoot,pathName,&handle);
}
LOCAL_C void Test5()
{
// Clamp requests on non-clamping file systems
test.Next(_L("T_Clamp - Test5()"));
TBuf<256> unsuppFile;
unsuppFile = _L("unsuppFile.tst");
RFile testFile;
TInt r=testFile.Replace(TheFs,unsuppFile,EFileWrite);
test(r==KErrNone);
// Try to clamp a file on a file system that does
// not support clamping
RFileClamp handle;
r=handle.Clamp(testFile);
test(r==KErrNotSupported);
// Tidy up
testFile.Close();
r=TheFs.Delete(_L("unsuppFile.tst"));
test (r==KErrNone);
}
LOCAL_C void GetDriveLetters()
{
// Assign the first drive that matches the required criteria
test.Next(_L("T_Clamp - GetDriveLetters()"));
TDriveList driveList;
TDriveInfo driveInfo;
TInt r=TheFs.DriveList(driveList);
test(r==KErrNone);
TInt drvNum;
TBool drivesFound = EFalse;
for(drvNum=0; (drvNum<KMaxDrives) && !drivesFound; drvNum++)
{
TChar drvLetter='?';
TFileName fileSystem;
if(!driveList[drvNum])
continue;
test(TheFs.Drive(driveInfo, drvNum) == KErrNone);
test(TheFs.DriveToChar(drvNum,drvLetter) == KErrNone);
r=TheFs.FileSystemName(fileSystem,drvNum);
fileSystem.UpperCase();
test((r==KErrNone)||(r==KErrNotFound));
if (!(driveInfo.iDriveAtt & KDriveAttInternal))
continue;
// Check for FAT on NAND
if(NandFatDrv=='?')
{
if((driveInfo.iType==EMediaNANDFlash) && (fileSystem.Compare(KFATName)==0))
NandFatDrv=drvLetter;
}
// Check for ROFS
if(RofsDrv=='?')
{
if((driveInfo.iType==EMediaNANDFlash) && (fileSystem.Compare(KROFSName)==0))
RofsDrv=drvLetter;
}
// Check for LFFS
if(LffsDrv=='?')
{
if((driveInfo.iType==EMediaFlash) && (fileSystem.Compare(KLFFSName)==0))
LffsDrv=drvLetter;
}
// Check for CompFSys
if(CompDrv=='?')
{
if((driveInfo.iType==EMediaRom) && ((fileSystem.Compare(KROMName)==0)||(fileSystem.Compare(KCOMPName)==0)))
CompDrv=drvLetter;
}
drivesFound=((NandFatDrv!='?')&&(RofsDrv!='?')&&(LffsDrv!='?')&&(CompDrv!='?'));
}
if(NandFatDrv!='?')
test((NandFatDrv!=RofsDrv)&&(NandFatDrv!=LffsDrv)&&(NandFatDrv!=CompDrv));
if(RofsDrv!='?')
test((RofsDrv!=LffsDrv)&&(RofsDrv!=CompDrv));
if(LffsDrv!='?')
test(LffsDrv!=CompDrv);
RDebug::Printf("T_CLAMP: FAT drive=%C, ROFS drive=%C, LFFS drive=%C, ROM-COMP drive=%C \n",(TText)NandFatDrv,(TText)RofsDrv,(TText)LffsDrv,(TText)CompDrv);
return;
}
//
// E32Main
//
TInt E32Main()
{
TInt r;
test.Title();
test.Start(_L("Starting T_CLAMP ..."));
test(TheFs.Connect()==KErrNone);
GetDriveLetters();
TBuf<256> pathName;
//************************************************************************
//
// Test on FAT (writable file system)
//
//************************************************************************
if(NandFatDrv!='?')
{
pathName=_L("?:\\CLAMP-TST\\"); // FAT on NAND
pathName[0]=(TText)NandFatDrv;
r=TheFs.MkDirAll(pathName);
test(r==KErrNone || r== KErrAlreadyExists);
TheFs.SetSessionPath(pathName);
test.Printf( _L("T_CLAMP: testing FAT drive on %C\n"),(TText)NandFatDrv);
Test1(); // Basic clamp operation
Test2(); // Invalid clamp requests
Test3(pathName);// Denied FS requests when files are clamped
r=TheFs.RmDir(pathName);
test(r==KErrNone);
}
else
test.Printf( _L("T_CLAMP: FAT drive not tested\n"));
//************************************************************************
//
// Test on ROFS (non-writable file system)
//
//************************************************************************
if(RofsDrv!='?')
{
pathName=_L("?:\\");
pathName[0]=(TText)RofsDrv;
TheFs.SetSessionPath(pathName);
test.Printf( _L("T_CLAMP: testing ROFS drive on %C\n"),(TText)RofsDrv);
Test4(pathName); // Clamp tests for non-writable file system
}
else
test.Printf( _L("T_CLAMP: ROFS drive not tested\n"));
//************************************************************************
//
// Test on Z: - Composite File System, or ROMFS (non-writable file system)
//
//************************************************************************
if(CompDrv!='?')
{
pathName=_L("?:\\TEST\\");
pathName[0]=(TText)CompDrv;
TheFs.SetSessionPath(pathName);
test.Printf( _L("T_CLAMP: testing Z drive (on %C)\n"),(TText)CompDrv);
Test4(pathName); // Clamp tests for non-writable file system
}
else
test.Printf( _L("T_CLAMP: Z drive not tested\n"));
//************************************************************************
//
// Test on LFFS (non-clampable file system)
//
//************************************************************************
if(LffsDrv!='?')
{
TBuf<256> unsuppPath;
unsuppPath=_L("?:\\CLAMP-TST\\");
unsuppPath[0]=(TText)LffsDrv;
r=TheFs.MkDirAll(unsuppPath);
test(r==KErrNone || r== KErrAlreadyExists);
TheFs.SetSessionPath(unsuppPath);
test.Printf( _L("T_CLAMP: testing LFFS drive on %C\n"),(TText)LffsDrv);
Test5(); // Clamp requests on non-clamping file systems
}
else
test.Printf( _L("T_CLAMP: LFFS drive not tested\n"));
test.End();
return 0;
}
#else
TInt E32Main()
{
test.Title();
test.Start(_L("Test does not run on UREL builds."));
test.End();
return 0;
}
#endif