sl@0: // Copyright (c) 1996-2009 Nokia Corporation and/or its subsidiary(-ies). sl@0: // All rights reserved. sl@0: // This component and the accompanying materials are made available sl@0: // under the terms of the License "Eclipse Public License v1.0" sl@0: // which accompanies this distribution, and is available sl@0: // at the URL "http://www.eclipse.org/legal/epl-v10.html". sl@0: // sl@0: // Initial Contributors: sl@0: // Nokia Corporation - initial contribution. sl@0: // sl@0: // Contributors: sl@0: // sl@0: // Description: sl@0: // f32test\server\t_handshare.cpp sl@0: // sl@0: // sl@0: sl@0: #include sl@0: #include sl@0: #include "t_server.h" sl@0: #include "handshare.h" sl@0: sl@0: GLDEF_D RTest test(_L("T_HANDSHARE")); sl@0: sl@0: LOCAL_D TInt drivenum; sl@0: sl@0: sl@0: sl@0: // test of (deprecated) RFile::Adopt() sl@0: // sl@0: // Request an open file (read only) sl@0: // sl@0: GLDEF_C void RequestFileDeprecatedAdopt() sl@0: { sl@0: test.Next(_L("RFile::Adopt()")); sl@0: sl@0: TInt r; sl@0: RFileHandleSharer handsvr; sl@0: do sl@0: { sl@0: r=handsvr.Connect(); sl@0: } sl@0: while(r==KErrNotFound); sl@0: test(r==KErrNone); sl@0: r=handsvr.SetTestDrive(drivenum); sl@0: test(r==KErrNone); sl@0: TInt ssh; sl@0: RFs fs1; sl@0: TInt fsh = handsvr.GetFileHandle(ssh, EFileRead); sl@0: sl@0: r = fs1.SetReturnedHandle(fsh); sl@0: test(r==KErrNone); sl@0: sl@0: RFile file; sl@0: r=file.Adopt(fs1,ssh); sl@0: test(r==KErrNone); sl@0: sl@0: TBuf8<100> rbuf; sl@0: r=file.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: sl@0: r=rbuf.CompareF(KTestData1()); sl@0: test(r==KErrNone); sl@0: sl@0: r=file.Write(KTestData()); sl@0: test(r==KErrAccessDenied); sl@0: sl@0: r=file.ChangeMode(EFileWrite); sl@0: test(r==KErrArgument); sl@0: sl@0: r=file.Rename(_L("\\newname.txt")); sl@0: test(r==KErrPermissionDenied || r==KErrAccessDenied); sl@0: sl@0: file.Close(); sl@0: sl@0: fsh = handsvr.GetFileHandle(ssh, EFileRead); sl@0: r = fs1.SetReturnedHandle(fsh); sl@0: test(r==KErrNone); sl@0: sl@0: // Adopt a bad sub-session handle sl@0: sl@0: r=file.Adopt(fs1, KNullHandle); sl@0: test(r==KErrBadHandle); sl@0: sl@0: r=file.Adopt(fs1, -1); sl@0: test(r==KErrBadHandle); sl@0: sl@0: sl@0: handsvr.Close(); sl@0: file.Close(); sl@0: RDebug::Print(_L("End Of Tests")); sl@0: fs1.Close(); sl@0: } sl@0: sl@0: sl@0: sl@0: // Cloning tests sl@0: GLDEF_C void Duplicate() sl@0: { sl@0: test.Next(_L("RFile::Duplicate()")); sl@0: sl@0: RFs fs; sl@0: TInt r=fs.Connect(); sl@0: test(r==KErrNone); sl@0: sl@0: // Check the number of open file handles sl@0: TInt resCount = fs.ResourceCount(); sl@0: test(resCount == 0); sl@0: sl@0: // create a file & fill it with data sl@0: RFile file1; sl@0: r=file1.Replace(fs,KCliFileName,EFileWrite); sl@0: test(r==KErrNone); sl@0: r=file1.Write(KTestData()); sl@0: test(r==KErrNone); sl@0: file1.Close(); sl@0: sl@0: // open the file for read sl@0: r = file1.Open(fs,KCliFileName,EFileRead); sl@0: test(r==KErrNone); sl@0: TBuf8<100> rbuf; sl@0: r = file1.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: r=rbuf.CompareF(KTestData); sl@0: test(r==KErrNone); sl@0: sl@0: sl@0: // clone the file sl@0: RFile file2; sl@0: r = file2.Duplicate(file1); sl@0: test(r==0); sl@0: sl@0: // make sure file positions are the same sl@0: TInt pos1 = 0; sl@0: r = file1.Seek(ESeekCurrent, pos1); sl@0: test(r==KErrNone); sl@0: TInt pos2 = 0; sl@0: r = file2.Seek(ESeekCurrent, pos2); sl@0: test(r==KErrNone); sl@0: test(pos1 == pos2); sl@0: sl@0: // change the position on the duplcated file handle & sl@0: // verify that the original file handle's position is unchanged sl@0: TInt oldPos1 = pos1; sl@0: sl@0: const TInt newPos2 = 5; sl@0: pos2 = newPos2; sl@0: r = file2.Seek(ESeekStart, pos2); sl@0: test(r==KErrNone); sl@0: sl@0: pos1 = 0; sl@0: r = file1.Seek(ESeekCurrent, pos1); sl@0: test(r==KErrNone); sl@0: test(pos1 == oldPos1); sl@0: sl@0: pos2 = 0; sl@0: r = file2.Seek(ESeekCurrent, pos2); sl@0: test(r==KErrNone); sl@0: test(pos2 == newPos2); sl@0: test(pos1 != pos2); sl@0: sl@0: // close the parent file and check we can still use the duplicated one. sl@0: file1.Close(); sl@0: sl@0: // Check the number of open file handles - should be 1 (the duplicated one) sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 1); sl@0: sl@0: fs.Close(); sl@0: sl@0: rbuf.FillZ(); sl@0: sl@0: // reset to pos 0 sl@0: pos2 = 0; sl@0: r = file2.Seek(ESeekStart, pos2); sl@0: test(r==KErrNone); sl@0: sl@0: r=file2.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: r=rbuf.CompareF(KTestData); sl@0: test(r==KErrNone); sl@0: file2.Close(); sl@0: sl@0: // start again - this time we're going to close the duplicated file first sl@0: // and check we can still use the parent file sl@0: sl@0: r = fs.Connect(); sl@0: test(r==KErrNone); sl@0: sl@0: // Make a note of the number of open resources sl@0: fs.ResourceCountMarkStart(); sl@0: sl@0: // open the file for read sl@0: r = file1.Open(fs,KCliFileName,EFileRead); sl@0: test(r==KErrNone); sl@0: sl@0: sl@0: // clone the file & check we can read it sl@0: r = file2.Duplicate(file1, EOwnerThread); sl@0: test(r==0); sl@0: rbuf.FillZ(); sl@0: r = file2.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: r=rbuf.CompareF(KTestData); sl@0: test(r==KErrNone); sl@0: sl@0: sl@0: // close the duplicated file and check we can still use the parent one. sl@0: file2.Close(); sl@0: sl@0: rbuf.FillZ(); sl@0: sl@0: // check we can read the parent file sl@0: r=file1.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: r=rbuf.CompareF(KTestData); sl@0: test(r==KErrNone); sl@0: sl@0: // close the parent sl@0: file1.Close(); sl@0: sl@0: // Check the number of open file handles sl@0: fs.ResourceCountMarkEnd(); sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 0); sl@0: sl@0: fs.Close(); sl@0: } sl@0: sl@0: sl@0: // Request an open file (write mode) from the server sl@0: // using RFile::AdoptFromServer() sl@0: GLDEF_C void RequestFileWrite() sl@0: { sl@0: TInt r; sl@0: RFileHandleSharer handsvr; sl@0: do sl@0: { sl@0: r=handsvr.Connect(); sl@0: } sl@0: while(r==KErrNotFound); sl@0: test(r==KErrNone); sl@0: sl@0: r=handsvr.SetTestDrive(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: TInt ssh; sl@0: TInt fsh = handsvr.GetFileHandle2(ssh, EFileWrite); sl@0: test (fsh >= 0); sl@0: sl@0: // Closing the handle to the server ensures the server has closed it's sl@0: // RFs and RFile handles - this provides a means of testing whether we sl@0: // can still adopt the RFile even if the server has closed it's one. sl@0: sl@0: handsvr.Sync(); // make sure server has finished doing what it's doing sl@0: handsvr.Close(); sl@0: sl@0: // adopt the file handle from FHServer sl@0: test.Next(_L("RFile::AdoptFromServer()")); sl@0: sl@0: RFile file; sl@0: r=file.AdoptFromServer(fsh, ssh); sl@0: test(r==KErrNone); sl@0: sl@0: TBuf8<100> rbuf; sl@0: r=file.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: sl@0: // server should write KTestData1 ("Server Write Server Write") to file sl@0: r=rbuf.CompareF(KTestData1); sl@0: test(r==KErrNone); sl@0: sl@0: // reset to pos 0 sl@0: TInt pos = 0; sl@0: r = file.Seek(ESeekStart, pos); sl@0: test(r==KErrNone); sl@0: sl@0: // overwrite with KTestData ("Client Write Client Write") to file sl@0: r=file.Write(KTestData()); sl@0: test(r==KErrNone); sl@0: rbuf.FillZ(); sl@0: r=file.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: r=rbuf.CompareF(KTestData); sl@0: test(r==KErrNone); sl@0: sl@0: // !!! Disable platform security tests until we get the new APIs sl@0: // r=file.Rename(_L("\\newname.txt")); sl@0: // test(r==KErrPermissionDenied); sl@0: sl@0: test.Next(_L("RFile::Name()")); sl@0: sl@0: // retrieve the file name from the server sl@0: TFileName name; sl@0: r = file.Name(name); sl@0: test(r==KErrNone); sl@0: r = name.Compare(KSvrFileName()); sl@0: test(r==0); sl@0: sl@0: sl@0: test.Next(_L("RFile::Duplicate()")); sl@0: RFile file2; sl@0: r = file2.Duplicate(file); sl@0: test(r==0); sl@0: sl@0: sl@0: TInt pos1 = 0; sl@0: r = file.Seek(ESeekCurrent, pos1); sl@0: test(r==KErrNone); sl@0: TInt pos2 = 0; sl@0: r = file2.Seek(ESeekCurrent, pos2); sl@0: test(r==KErrNone); sl@0: test(pos1 == pos2); sl@0: sl@0: // close the parent file and check we can still use the duplicated one. sl@0: file.Close(); sl@0: sl@0: rbuf.FillZ(); sl@0: sl@0: // reset to pos 0 sl@0: pos2 = 0; sl@0: r = file2.Seek(ESeekStart, pos2); sl@0: test(r==KErrNone); sl@0: sl@0: r=file2.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: r=rbuf.CompareF(KTestData); sl@0: test(r==KErrNone); sl@0: file2.Close(); sl@0: } sl@0: sl@0: sl@0: // Request a test file & test what we can do with it sl@0: // i.e CFileMan::Copy, RFile::Rename() and RFs:Delete() sl@0: // sl@0: void RequestFileTest() sl@0: { sl@0: TInt r; sl@0: sl@0: RFs fs; sl@0: r=fs.Connect(); sl@0: test(r==KErrNone); sl@0: r=fs.ShareProtected(); sl@0: test(r==KErrNone); sl@0: sl@0: sl@0: // define a filename in our private path sl@0: TPath newPath; sl@0: fs.PrivatePath(newPath); sl@0: TFileName newFileName; sl@0: newFileName = newPath; sl@0: newFileName.Append(_L("newname.txt")); sl@0: sl@0: r=fs.CreatePrivatePath(drivenum); sl@0: test(r==KErrNone); sl@0: r=fs.SetSessionToPrivate(drivenum); sl@0: sl@0: RFileHandleSharer handsvr; sl@0: do sl@0: { sl@0: r=handsvr.Connect(); sl@0: } sl@0: while(r==KErrNotFound); sl@0: test(r==KErrNone); sl@0: sl@0: r=handsvr.SetTestDrive(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: // Next verify that we can copy a file retrieved from the server sl@0: // using CFileMan::Copy() sl@0: sl@0: test.Next(_L("CFileMan::Copy()")); sl@0: sl@0: TInt ssh; sl@0: TInt fsh = handsvr.GetFileHandle2(ssh, EFileRead); sl@0: test (fsh >= 0); sl@0: sl@0: RFile file; sl@0: r=file.AdoptFromServer(fsh, ssh); sl@0: test(r==KErrNone); sl@0: sl@0: sl@0: CFileMan* fileMan = NULL; sl@0: TRAP(r, fileMan = CFileMan::NewL(fs)); sl@0: test(r == KErrNone && fileMan != NULL); sl@0: sl@0: // copy to file, overwrite sl@0: r = fileMan->Copy(file, newFileName, CFileMan::EOverWrite); sl@0: test(r == KErrNone); sl@0: sl@0: // copy to file, don't overwrite sl@0: r = fileMan->Copy(file, newFileName, 0); sl@0: test(r == KErrAlreadyExists); sl@0: sl@0: // copy to file, overwrite sl@0: r = fileMan->Copy(file, newFileName, CFileMan::EOverWrite); sl@0: test(r == KErrNone); sl@0: sl@0: // copy to path sl@0: r = fileMan->Copy(file, newPath, CFileMan::EOverWrite); sl@0: test(r == KErrNone); sl@0: sl@0: // copy to file, overwrite, asynchnonous sl@0: TRequestStatus status(KRequestPending); sl@0: r = fileMan->Copy(file, newFileName, CFileMan::EOverWrite, status); sl@0: test(r == KErrNone); sl@0: User::WaitForRequest(status); sl@0: test(status == KErrNone); sl@0: sl@0: sl@0: // Negative tests... sl@0: TPath newLongPath; sl@0: TInt len; sl@0: sl@0: // copy to very long but valid path (no filename) which will overflow sl@0: // when the filename is appended to it sl@0: newLongPath = newPath; sl@0: for (len=newLongPath.Length(); len< KMaxPath -4; len = newLongPath.Length()) sl@0: newLongPath.Append(_L("x\\")); sl@0: r = fileMan->Copy(file, newLongPath, CFileMan::EOverWrite); sl@0: test(r == KErrBadName); sl@0: sl@0: // copy to very long but valid path (no filename) which will overflow sl@0: // when drive letter is pre-pended to it sl@0: newLongPath = newPath; sl@0: for (len=newLongPath.Length(); len< KMaxPath -2; len = newLongPath.Length()) sl@0: newLongPath.Append(_L("x\\")); sl@0: r = fileMan->Copy(file, newLongPath, CFileMan::EOverWrite); sl@0: test(r == KErrBadName); sl@0: sl@0: // copy to very long but valid path and filename which will overflow sl@0: // when drive letter is pre-pended to it sl@0: newLongPath.Append(_L("y")); sl@0: r = fileMan->Copy(file, newLongPath, CFileMan::EOverWrite); sl@0: test(r == KErrBadName); sl@0: sl@0: // copy to badly formed path sl@0: newLongPath = newPath; sl@0: newLongPath.Append(_L("\\y")); sl@0: r = fileMan->Copy(file, newLongPath, CFileMan::EOverWrite); sl@0: test(r == KErrBadName); sl@0: sl@0: // copy to correctly formed path which doesn't exist sl@0: newLongPath = newPath; sl@0: newLongPath.Append(_L("x\\y\\z")); sl@0: r = fileMan->Copy(file, newLongPath, CFileMan::EOverWrite); sl@0: test(r == KErrPathNotFound); sl@0: sl@0: delete fileMan; fileMan = NULL; sl@0: sl@0: file.Close(); sl@0: sl@0: sl@0: // First verify that we CANNOT rename a file retrieved from the server sl@0: // that has not been opened in EFileShareExclusive mode sl@0: sl@0: test.Next(_L("negative test of RFile::Rename()")); sl@0: sl@0: fsh = handsvr.GetFileHandle2(ssh, TFileMode(EFileShareAny | EFileWrite)); sl@0: test (fsh >= 0); sl@0: sl@0: // adopt the file handle from FHServer sl@0: r=file.AdoptFromServer(fsh, ssh); sl@0: test(r==KErrNone); sl@0: sl@0: r=file.Rename(_L("newname.txt")); sl@0: test(r==KErrPermissionDenied || r==KErrAccessDenied); sl@0: sl@0: // delete the file before we try to rename anything to it sl@0: r = fs.Delete(newFileName); sl@0: test(r == KErrNone || r == KErrNotFound); sl@0: sl@0: r=file.Rename(newFileName); sl@0: test(r==KErrPermissionDenied || r==KErrAccessDenied); sl@0: sl@0: file.Close(); sl@0: sl@0: sl@0: // Next verify that we CAN rename a file retrieved from the server sl@0: // that HAS been opened in EFileShareExclusive mode sl@0: sl@0: test.Next(_L("RFile::Rename()")); sl@0: sl@0: fsh = handsvr.GetFileHandle2(ssh, EFileWrite); sl@0: test (fsh >= 0); sl@0: sl@0: r=file.AdoptFromServer(fsh, ssh); sl@0: test(r==KErrNone); sl@0: sl@0: // delete the file before we try to rename anything to it sl@0: r = fs.Delete(newFileName); sl@0: test(r == KErrNone || r == KErrNotFound); sl@0: sl@0: r=file.Rename(newFileName); sl@0: test(r==KErrNone); sl@0: sl@0: file.Close(); sl@0: sl@0: // Next verify that we can delete the file (which should now sl@0: // have been moved to our private directory) sl@0: test.Next(_L("RFs::Delete()")); sl@0: r = fs.Delete(newFileName); sl@0: test(r == KErrNone); sl@0: sl@0: handsvr.Close(); sl@0: sl@0: fs.Close(); sl@0: } sl@0: sl@0: // sl@0: // Pass an open file to the server sl@0: // The server will use RFile::AdoptFromClient() sl@0: // sl@0: GLDEF_C void PassFile() sl@0: { sl@0: RFs fs; sl@0: TInt r=fs.Connect(); sl@0: test(r==KErrNone); sl@0: sl@0: // Check the number of open file handles sl@0: TInt resCount = fs.ResourceCount(); sl@0: test(resCount == 0); sl@0: sl@0: r=fs.ShareProtected(); sl@0: test(r==KErrNone); sl@0: sl@0: r=fs.CreatePrivatePath(drivenum); sl@0: test(r==KErrNone); sl@0: r=fs.SetSessionToPrivate(drivenum); sl@0: sl@0: sl@0: RFile file1; sl@0: r=file1.Replace(fs,KCliFileName,EFileWrite); sl@0: test(r==KErrNone); sl@0: r=file1.Write(KTestData()); sl@0: test(r==KErrNone); sl@0: file1.Close(); sl@0: sl@0: RFileHandleSharer handsvr; sl@0: do sl@0: { sl@0: r=handsvr.Connect(); sl@0: } sl@0: while(r==KErrNotFound); sl@0: test(r==KErrNone); sl@0: sl@0: r=handsvr.SetTestDrive(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: r=fs.SetSessionToPrivate(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: r=file1.Open(fs,KCliFileName,EFileRead); sl@0: test(r==KErrNone); sl@0: sl@0: // pass the file handle to FHServer sl@0: test.Next(_L("RFile::TransferToServer()")); sl@0: sl@0: TIpcArgs ipcArgs; sl@0: file1.TransferToServer(ipcArgs, 0, 1); sl@0: sl@0: r = handsvr.PassFileHandle(ipcArgs); sl@0: sl@0: sl@0: // verify that the original file handle's position is unchanged sl@0: TInt pos = 0; sl@0: r = file1.Seek(ESeekCurrent, pos); sl@0: test(r==KErrNone); sl@0: test(pos == 0); sl@0: sl@0: // make sure we can still use it sl@0: TBuf8<100> rbuf; sl@0: r=file1.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: sl@0: // Close the file sl@0: file1.Close(); sl@0: sl@0: handsvr.Close(); sl@0: sl@0: r=fs.MkDir(_L("C:\\mdir")); sl@0: test(r==KErrNone || r==KErrAlreadyExists); sl@0: sl@0: // Check the number of open file handles sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 0); sl@0: sl@0: fs.Close(); sl@0: } sl@0: sl@0: sl@0: // sl@0: // Pass an invalid file handle to the server sl@0: // The server will use RFile::AdoptFromClient() sl@0: // sl@0: GLDEF_C void PassInvalidFile() sl@0: { sl@0: sl@0: RFs fs; sl@0: TInt r=fs.Connect(); sl@0: test(r==KErrNone); sl@0: sl@0: // Check the number of open file handles sl@0: TInt resCount = fs.ResourceCount(); sl@0: test(resCount == 0); sl@0: sl@0: r=fs.ShareProtected(); sl@0: test(r==KErrNone); sl@0: sl@0: r=fs.CreatePrivatePath(drivenum); sl@0: test(r==KErrNone); sl@0: r=fs.SetSessionToPrivate(drivenum); sl@0: sl@0: sl@0: RFile file1; sl@0: r=file1.Replace(fs,KCliFileName,EFileWrite); sl@0: test(r==KErrNone); sl@0: r=file1.Write(KTestData()); sl@0: test(r==KErrNone); sl@0: file1.Close(); sl@0: sl@0: RFileHandleSharer handsvr; sl@0: do sl@0: { sl@0: r=handsvr.Connect(); sl@0: } sl@0: while(r==KErrNotFound); sl@0: test(r==KErrNone); sl@0: sl@0: r=handsvr.SetTestDrive(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: r=fs.SetSessionToPrivate(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: r=file1.Open(fs,KCliFileName,EFileRead); sl@0: test(r==KErrNone); sl@0: sl@0: // check the resoure count - there should be 1 open file handle sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 1); sl@0: sl@0: // pass an invalid file handle to FHServer sl@0: // by overwriting the IPC slots sl@0: test.Next(_L("PassInvalidFileHandle - RFile::TransferToServer()")); sl@0: sl@0: TIpcArgs ipcArgs; sl@0: sl@0: // Pass a bad RFs handle sl@0: file1.TransferToServer(ipcArgs, 0, 1); sl@0: sl@0: // check the resoure count - there should be 2 open file handles sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 2); sl@0: sl@0: ipcArgs.Set(0, 0); // invalidate the RFs handle sl@0: r = handsvr.PassInvalidFileHandle(ipcArgs); sl@0: test (r == KErrBadHandle); sl@0: sl@0: // Pass a bad RFile handle sl@0: file1.TransferToServer(ipcArgs, 0, 1); sl@0: sl@0: // check the resoure count - there should be 3 open file handles sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 3); sl@0: sl@0: ipcArgs.Set(1, 0); // invalidate the RFile handle sl@0: r = handsvr.PassInvalidFileHandle(ipcArgs); sl@0: test (r == KErrBadHandle); sl@0: sl@0: // Pass bad RFs and RFile handles sl@0: file1.TransferToServer(ipcArgs, 0, 1); sl@0: sl@0: // check the resoure count - there should be 4 open file handles sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 4); sl@0: sl@0: sl@0: ipcArgs.Set(0, 0); // invalidate the RFs handle sl@0: ipcArgs.Set(1, 0); // invalidate the RFile handle sl@0: r = handsvr.PassInvalidFileHandle(ipcArgs); sl@0: test (r == KErrBadHandle); sl@0: sl@0: // Close the file sl@0: handsvr.Close(); sl@0: file1.Close(); sl@0: sl@0: // Check the number of open file handles sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 3); sl@0: sl@0: fs.Close(); sl@0: } sl@0: sl@0: sl@0: // Pass RFs/RFile handles to the server using sl@0: // process parameter slots (RProcess::SetParameter()), sl@0: // resume the process and wait for it to read the file... sl@0: // The server will use RFile::AdoptFromCreator() sl@0: GLDEF_C void PassFile(RProcess& aProcess) sl@0: { sl@0: sl@0: RFs fs; sl@0: TInt r=fs.Connect(); sl@0: test(r==KErrNone); sl@0: sl@0: // Check the number of open file handles sl@0: TInt resCount = fs.ResourceCount(); sl@0: test(resCount == 0); sl@0: sl@0: r=fs.ShareProtected(); sl@0: test(r==KErrNone); sl@0: sl@0: r=fs.CreatePrivatePath(drivenum); sl@0: test(r==KErrNone); sl@0: r=fs.SetSessionToPrivate(drivenum); sl@0: sl@0: sl@0: RFile file1; sl@0: r=file1.Replace(fs,KCliFileName,EFileWrite); sl@0: test(r==KErrNone); sl@0: r=file1.Write(KTestData()); sl@0: test(r==KErrNone); sl@0: file1.Close(); sl@0: sl@0: r=file1.Open(fs, KCliFileName, EFileWrite); sl@0: sl@0: test(r==KErrNone); sl@0: sl@0: // NB slot 0 is reserved for the command line sl@0: sl@0: test.Next(_L("RFile::TransferToProcess()")); sl@0: sl@0: r = file1.TransferToProcess(aProcess, 1, 2); sl@0: sl@0: r = aProcess.SetParameter(3, drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: r=fs.SetSessionToPrivate(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: // make sure we can still read from the file sl@0: TBuf8<100> rbuf; sl@0: r=file1.Read(0,rbuf); sl@0: test(r==KErrNone); sl@0: r=rbuf.CompareF(KTestData()); sl@0: test(r==KErrNone); sl@0: file1.Close(); sl@0: sl@0: r=fs.MkDir(_L("C:\\mdir")); sl@0: test(r==KErrNone || r==KErrAlreadyExists); sl@0: sl@0: // Check the number of open file handles - sl@0: // should be 1 (the one duplicated for the other process) sl@0: resCount = fs.ResourceCount(); sl@0: test(resCount == 1); sl@0: sl@0: fs.Close(); sl@0: sl@0: // Start the server thread sl@0: aProcess.Resume(); sl@0: sl@0: sl@0: sl@0: // connect to the server sl@0: RFileHandleSharer handsvr; sl@0: do sl@0: { sl@0: r=handsvr.Connect(); sl@0: } sl@0: while(r==KErrNotFound); sl@0: test(r==KErrNone); sl@0: sl@0: sl@0: r=handsvr.SetTestDrive(drivenum); sl@0: test(r==KErrNone); sl@0: sl@0: // wait for server to read the file sl@0: r = handsvr.PassFileHandleProcess(); sl@0: test (r == KErrNone); sl@0: sl@0: handsvr.Close(); sl@0: } sl@0: sl@0: sl@0: sl@0: GLDEF_C void CallTestsL(void) sl@0: { sl@0: RFs::CharToDrive(gDriveToTest,drivenum); sl@0: sl@0: // make sure the session path exists sl@0: RFs fs; sl@0: TInt r = fs.Connect(); sl@0: test(r==KErrNone); sl@0: sl@0: TFileName sessionp; sl@0: fs.SessionPath(sessionp); sl@0: r = fs.MkDirAll(sessionp); sl@0: test(r==KErrNone || r==KErrAlreadyExists); sl@0: fs.Close(); sl@0: sl@0: // Remember the number of open handles. Just for a sanity check .... sl@0: TInt start_thc, start_phc; sl@0: RThread().HandleCount(start_phc, start_thc); sl@0: test.Printf(_L("Handles: start_phc %d, start_thc %d\n"), start_phc, start_thc); sl@0: sl@0: //create test server sl@0: RProcess p; sl@0: r = p.Create(_L("FHServer.exe"), KNullDesC); sl@0: test(r==KErrNone); sl@0: sl@0: // RFile::Duplicate() tests sl@0: Duplicate(); sl@0: sl@0: // Pass RFs/RFile handles to the server using RFile::TransferToProcess() sl@0: // process parameter slots (RProcess::SetParameter()), sl@0: // resume the server process and wait for it to read the file... sl@0: PassFile(p); sl@0: sl@0: // Transfer the file handle to FHServer using RFile::TransferToServer(). sl@0: // Get FHServer to transfer it to FHServer2 sl@0: PassFile(); sl@0: sl@0: sl@0: // Get an open writeable file from FHServer2 via FHServer sl@0: // using RFile::AdoptFromServer() sl@0: RequestFileWrite(); sl@0: sl@0: // Deprecated RFile::Adopt() test sl@0: RequestFileDeprecatedAdopt(); sl@0: sl@0: // negative test sl@0: // Pass an invalid file handle to the server sl@0: PassInvalidFile(); sl@0: sl@0: sl@0: // Get an open file handle from FHServer2 via FHServer sl@0: // and test whether we can copy/rename/delete it etc sl@0: // be able to rename it. sl@0: RequestFileTest(); sl@0: sl@0: // stop the servers sl@0: RFileHandleSharer handsvr; sl@0: r=handsvr.Connect(); sl@0: test(r==KErrNone); sl@0: r = handsvr.Exit(); sl@0: test(r == KErrNone); sl@0: handsvr.Close(); sl@0: sl@0: // delete the test file sl@0: RFs cleanupfs; sl@0: r=cleanupfs.Connect(); sl@0: test(r==KErrNone); sl@0: r=cleanupfs.SetSessionToPrivate(drivenum); sl@0: test(r==KErrNone); sl@0: r=cleanupfs.Delete(KCliFileName); sl@0: test(r==KErrNone || r==KErrNotFound); sl@0: cleanupfs.Close(); sl@0: sl@0: sl@0: // wait for server process to end sl@0: TRequestStatus status; sl@0: p.Logon(status); sl@0: User::WaitForRequest(status); sl@0: test (status == KErrNone); sl@0: sl@0: // cleanup sl@0: p.Close(); sl@0: sl@0: // Sanity check for open handles sl@0: TInt end_thc, end_phc; sl@0: RThread().HandleCount(end_phc, end_thc); sl@0: test.Printf(_L("Handles: end_phc %d, end_thc %d\n"), end_phc, end_thc); sl@0: sl@0: test(start_thc == end_thc); sl@0: test(start_phc == end_phc); sl@0: sl@0: // and also for pending requests ... sl@0: test(RThread().RequestCount() == 0); sl@0: sl@0: sl@0: RDebug::Print(_L("End Of Tests")); sl@0: } sl@0: sl@0: sl@0: