userlibandfileserver/fileserver/sfile/sf_request.cpp
changeset 273 6a75fa55495f
parent 243 c7a0ce20c48c
child 286 48e57fb1237e
equal deleted inserted replaced
271:dc268b18d709 273:6a75fa55495f
   367 
   367 
   368 CFsRequest::~CFsRequest()
   368 CFsRequest::~CFsRequest()
   369 //
   369 //
   370 //
   370 //
   371 //
   371 //
   372 	{}
   372 	{
       
   373 	Close();
       
   374 	}
   373 
   375 
   374 void CFsRequest::Set(const TOperation& aOperation,CSessionFs* aSession)
   376 void CFsRequest::Set(const TOperation& aOperation,CSessionFs* aSession)
   375 //
   377 //
   376 //
   378 //
   377 //
   379 //
   378 	{
   380 	{
   379 
   381 
   380 	SetState(EReqStateInitialise);
   382 	SetState(EReqStateInitialise);
   381 
   383 
   382 	iOperation     = const_cast<TOperation*>(&aOperation);
   384 	iOperation     = const_cast<TOperation*>(&aOperation);
   383 	iSession       = aSession;
   385 	Set(aSession);
   384 	iIsCompleted   = aOperation.IsCompleted();
       
   385 	iError         = KErrNone;
       
   386 	iDriveNumber   = KDriveInvalid;
       
   387 	iCurrentPlugin = NULL;
       
   388 	iOwnerPlugin   = NULL;
       
   389 	iDirectToDrive = EFalse;
       
   390 	iClientThreadId= 0;
       
   391 	iFlags &= ~(EFreeChanged | EPostInterceptEnabled | EPostOperation | EFsObjectOpen);
       
   392 	iScratchValue = 0;
       
   393 	}
   386 	}
   394 
   387 
   395 void CFsRequest::Set(CSessionFs* aSession)
   388 void CFsRequest::Set(CSessionFs* aSession)
   396 //
   389 //
   397 //
   390 //
   399 	{
   392 	{
   400 	__ASSERT_DEBUG(iOperation,Fault(EBaseRequestSet1));
   393 	__ASSERT_DEBUG(iOperation,Fault(EBaseRequestSet1));
   401 
   394 
   402 	SetState(EReqStateInitialise);
   395 	SetState(EReqStateInitialise);
   403 
   396 
   404 	iSession       = aSession;
       
   405 	iIsCompleted   = iOperation->IsCompleted();
   397 	iIsCompleted   = iOperation->IsCompleted();
   406 	iError         = KErrNone;
   398 	iError         = KErrNone;
   407 	iDriveNumber   = KDriveInvalid;
   399 	iDriveNumber   = KDriveInvalid;
   408 	iCurrentPlugin = NULL;
   400 	iCurrentPlugin = NULL;
   409 	iOwnerPlugin   = NULL;
   401 	iOwnerPlugin   = NULL;
   410 	iDirectToDrive = EFalse;
   402 	iDirectToDrive = EFalse;
   411 	iClientThreadId= 0;
   403 	iClientThreadId= 0;
   412 	iFlags &= ~(EFreeChanged | EPostInterceptEnabled | EPostOperation | EFsObjectOpen);
   404 	iFlags &= ~(EFreeChanged | EPostInterceptEnabled | EPostOperation | EFsDspObjOpen);
       
   405 
   413 	iScratchValue = 0;
   406 	iScratchValue = 0;
       
   407 
       
   408 	OpenSession(aSession);
   414 	}
   409 	}
   415 
   410 
   416 
   411 
   417 TParse& CFsRequest::Src()
   412 TParse& CFsRequest::Src()
   418 //
   413 //
   641 		}
   636 		}
   642 	
   637 	
   643 	return KErrNotSupported;
   638 	return KErrNotSupported;
   644 	}
   639 	}
   645 
   640 
   646 void CFsRequest::SetAndOpenScratchValue(const TInt64& aValue)
   641 void CFsRequest::OpenDispatchObject(const TInt64& aValue)
   647 	{
   642 	{
   648 	if (IsFsObjectOpen())
   643 	CloseDispatchObject();
       
   644 
       
   645 	iScratchValue = aValue;
       
   646 
       
   647 	if (I64LOW(iScratchValue) && iOperation && (iOperation->iFlags & EFsDspObj))
       
   648 		{
       
   649 		((CFsDispatchObject*) I64LOW(iScratchValue))->Open();
       
   650 		iFlags |= EFsDspObjOpen;
       
   651 		}
       
   652 	}
       
   653 
       
   654 void CFsRequest::CloseDispatchObject()
       
   655 	{
       
   656 	if (iFlags & EFsDspObjOpen)
   649 		{
   657 		{
   650 		((CFsDispatchObject*) I64LOW(iScratchValue))->Close();
   658 		((CFsDispatchObject*) I64LOW(iScratchValue))->Close();
   651 		SetFsObjectOpen(EFalse);
   659 		iFlags &= ~EFsDspObjOpen;
   652 		}
   660 		}
   653 	if (I64LOW(aValue) && iOperation && (iOperation->iFlags & EFileShare))
   661 	}
   654 		{
   662 
   655 		((CFsDispatchObject*) I64LOW(aValue))->Open();
   663 void CFsRequest::OpenSession(CSessionFs* aSession)
   656 		SetFsObjectOpen(ETrue);
   664 	{
   657 		}
   665 	CloseSession();
   658 	iScratchValue = aValue;
   666 	iSession = aSession;
   659 	}
   667 	if (iSession)
   660 
   668 		iSession->Open();
       
   669 	}
       
   670 
       
   671 void CFsRequest::CloseSession()
       
   672 	{
       
   673 	if (iSession)
       
   674 		{
       
   675 		iSession->Close();
       
   676 		iSession = NULL;
       
   677 		}
       
   678 	}
       
   679 
       
   680 void CFsRequest::Close()
       
   681 	{
       
   682 	SetScratchValue(0);	// this should close the CFsObject
       
   683 	CloseSession();
       
   684 	}
   661 
   685 
   662 TInt CFsRequest::Read(TFsPluginRequest::TF32ArgType aType, TDes8& aDes, TInt aOffset)
   686 TInt CFsRequest::Read(TFsPluginRequest::TF32ArgType aType, TDes8& aDes, TInt aOffset)
   663 	{
   687 	{
   664 	TInt slot = GetSlot(aType);
   688 	TInt slot = GetSlot(aType);
   665 	if(slot >= 0)
   689 	if(slot >= 0)
  1356 //
  1380 //
  1357 //
  1381 //
  1358 	{
  1382 	{
  1359 	__THRD_PRINT1(_L("CFsMessageRequest::Free() isAllocated=%d"), IsAllocated());
  1383 	__THRD_PRINT1(_L("CFsMessageRequest::Free() isAllocated=%d"), IsAllocated());
  1360 
  1384 
  1361 	SetScratchValue(0);	// this should close the CFsObject
  1385 	Close();
  1362 
  1386 
  1363 	if(!IsAllocated())
  1387 	if(!IsAllocated())
  1364 		delete(this);
  1388 		delete(this);
  1365 	else iOperation = NULL;
  1389 	else iOperation = NULL;
  1366 
  1390 
  1960 		{
  1984 		{
  1961 		TParsePool::Release(iPoolDest);
  1985 		TParsePool::Release(iPoolDest);
  1962 		iPoolDest = 0;
  1986 		iPoolDest = 0;
  1963 		}
  1987 		}
  1964 
  1988 
  1965 	SetScratchValue(0);	// this should close the CFsObject
  1989 	Close();
       
  1990 
  1966 	iOperation = NULL;
  1991 	iOperation = NULL;
  1967 	RequestAllocator::FreeRequest(this);
  1992 	RequestAllocator::FreeRequest(this);
  1968 	}
  1993 	}
  1969 
  1994 
  1970 
  1995 
  2168 //
  2193 //
  2169 //
  2194 //
  2170 	{
  2195 	{
  2171 	__PRINT1(_L("CFsInternalRequest::Complete() with %d"),aError);
  2196 	__PRINT1(_L("CFsInternalRequest::Complete() with %d"),aError);
  2172 	TInt func = Operation()->Function();
  2197 	TInt func = Operation()->Function();
  2173 	if(func==KCancelSession || func==KCancelPlugin || func==KFlushDirtyData)
  2198 	if(func == KDispatchObjectClose)
  2174 		{
       
  2175 		__ASSERT_DEBUG(ThreadHandle()!=0 && !FsThreadManager::IsDisconnectThread(),Fault(EInternalRequestComplete1));
       
  2176 		RThread t;
       
  2177 		t.SetHandle(ThreadHandle());
       
  2178 		TRequestStatus* s=&Status();
       
  2179 		t.RequestComplete(s,aError);
       
  2180 		Free();
       
  2181 		}
       
  2182 	else if(func == KDispatchObjectClose)
       
  2183 		{
  2199 		{
  2184 		TFsCloseObject::Complete(this);
  2200 		TFsCloseObject::Complete(this);
  2185 		Free();
  2201 		Free();
  2186 		}
  2202 		}
  2187 	else if(func==KFileShareClose)
  2203 	else if(func==KFileShareClose)
  2206 //
  2222 //
  2207 	{
  2223 	{
  2208 	__THRD_PRINT(_L("CFsInternalRequest::Dispatch()"));
  2224 	__THRD_PRINT(_L("CFsInternalRequest::Dispatch()"));
  2209 	__ASSERT_ALWAYS(Initialise()==KErrNone,Fault(EInternalRequestDispatch1));
  2225 	__ASSERT_ALWAYS(Initialise()==KErrNone,Fault(EInternalRequestDispatch1));
  2210 
  2226 
  2211 	if(iCurrentPlugin && Operation()->Function() == KCancelPlugin)
  2227 	TInt drivenumber = DriveNumber();
  2212 		{
  2228 	FsThreadManager::LockDrive(drivenumber);
  2213 		TFsPluginRequest request(this);
  2229 	// shouldn't dispath if no drive available
  2214 		TInt r = iCurrentPlugin->Deliver(request);
  2230 	__ASSERT_ALWAYS(FsThreadManager::IsDriveAvailable(drivenumber,EFalse) && !FsThreadManager::IsDriveSync(drivenumber,EFalse),Fault(EInternalRequestDispatch2));
  2215 		__ASSERT_ALWAYS(r == KErrNone, Fault(EInternalRequestDispatchCancelPlugin));
  2231 	CDriveThread* dT=NULL;
  2216 		}
  2232 	TInt r=FsThreadManager::GetDriveThread(drivenumber,&dT);
       
  2233 	__THRD_PRINT2(_L("deliver to thread 0x%x, drive number %d"),dT,drivenumber);
       
  2234 	__ASSERT_ALWAYS(r==KErrNone && dT,Fault(EInternalRequestDispatch3));
       
  2235 	CRequestThread* pT = (CRequestThread*)dT;
       
  2236 	TInt func = Operation()->Function();
       
  2237 	if(func == KDispatchObjectClose || func == KFileShareClose || func == KFlushDirtyData)
       
  2238 		pT->DeliverBack(this);
  2217 	else
  2239 	else
  2218 		{
  2240 		pT->DeliverFront(this);
  2219 		TInt drivenumber = DriveNumber();
  2241 	FsThreadManager::UnlockDrive(drivenumber);
  2220 		FsThreadManager::LockDrive(drivenumber);
       
  2221 		// shouldn't dispath if no drive available
       
  2222 		__ASSERT_ALWAYS(FsThreadManager::IsDriveAvailable(drivenumber,EFalse) && !FsThreadManager::IsDriveSync(drivenumber,EFalse),Fault(EInternalRequestDispatch2));
       
  2223 		CDriveThread* dT=NULL;
       
  2224 		TInt r=FsThreadManager::GetDriveThread(drivenumber,&dT);
       
  2225 		__THRD_PRINT2(_L("deliver to thread 0x%x, drive number %d"),dT,drivenumber);
       
  2226 		__ASSERT_ALWAYS(r==KErrNone && dT,Fault(EInternalRequestDispatch3));
       
  2227 		CRequestThread* pT = (CRequestThread*)dT;
       
  2228 		TInt func = Operation()->Function();
       
  2229 		if(func == KDispatchObjectClose || func == KFileShareClose || func == KFlushDirtyData)
       
  2230 			pT->DeliverBack(this);
       
  2231 		else
       
  2232 			pT->DeliverFront(this);
       
  2233 		FsThreadManager::UnlockDrive(drivenumber);
       
  2234 		}
       
  2235 	}
  2242 	}
  2236 
  2243 
  2237 void CFsInternalRequest::Free()
  2244 void CFsInternalRequest::Free()
  2238 //
  2245 //
  2239 //
  2246 //
  2240 //
  2247 //
  2241 	{
  2248 	{
  2242 	__THRD_PRINT1(_L("CFsInternalRequest::Free() isAllocated=%d"),IsAllocated());
  2249 	__THRD_PRINT1(_L("CFsInternalRequest::Free() isAllocated=%d"),IsAllocated());
  2243 
  2250 
  2244 	SetScratchValue(0);	// this should close the CFsObject
  2251 	Close();
  2245 
  2252 
  2246 	if(!IsAllocated())
  2253 	if(!IsAllocated())
  2247 		delete(this);
  2254 		delete(this);
  2248 	}
       
  2249 
       
  2250 void CFsDisconnectRequest::Dispatch()
       
  2251 //
       
  2252 //
       
  2253 //
       
  2254 	{
       
  2255 	__THRD_PRINT(_L("CFsDisconnectRequest::Dispatch()"));
       
  2256 	// no need to lock
       
  2257 	TInt r=Initialise();
       
  2258 	__ASSERT_ALWAYS(r==KErrNone,Fault(EDisconnectRequestDispatch1));
       
  2259 	CRequestThread* pT=FsThreadManager::GetDisconnectThread();
       
  2260 	__ASSERT_ALWAYS(pT,Fault(EDisconnectRequestDispatch2));
       
  2261 	pT->DeliverBack(this);
       
  2262 	}
       
  2263 
       
  2264 void CFsDisconnectRequest::Process()
       
  2265 //
       
  2266 //
       
  2267 //
       
  2268 	{
       
  2269 	__THRD_PRINT(_L("CFsDisconnectRequest::Process()"));
       
  2270 	TInt r=KErrNone;
       
  2271 	TRAPD(leaveValue,r=iOperation->DoRequestL(this));
       
  2272 	leaveValue=leaveValue; // just to make compiler happy
       
  2273 	__ASSERT_DEBUG(leaveValue==KErrNone && r==KErrNone,Fault(EDisonncectRequestProcess));
       
  2274 	Complete(r);
       
  2275 	}
       
  2276 
       
  2277 void CFsDisconnectRequest::Complete(TInt aError)
       
  2278 //
       
  2279 //
       
  2280 //
       
  2281 	{
       
  2282 	__PRINT1(_L("CFsDisconnectRequest::Complete() with %d"),aError);
       
  2283 	__ASSERT_ALWAYS(aError==KErrNone,Fault(EDisconnectRequestComplete));
       
  2284 	// set session disconnect reqeust to NULL
       
  2285 	// will be freed in CFsMessageRequest::Free()
       
  2286 	Session()->iDisconnectRequest=NULL;
       
  2287 	// now delete session
       
  2288 	TheFileServer->SessionQueueLockWait();
       
  2289 	delete(Session());
       
  2290 	TheFileServer->SessionQueueLockSignal();
       
  2291 	// NB Must complete the message AFTER the session has been deleted...
       
  2292 	Message().Complete(aError);
       
  2293 	delete(this);	
       
  2294 	}
  2255 	}
  2295 
  2256 
  2296 
  2257 
  2297 /**
  2258 /**
  2298 Create a new synchronous message scheduler
  2259 Create a new synchronous message scheduler
  2408 		iLock.Signal();
  2369 		iLock.Signal();
  2409 		}
  2370 		}
  2410 	}
  2371 	}
  2411 
  2372 
  2412 
  2373 
  2413 /**
       
  2414 Complete outstanding requests for the specified session
       
  2415 */
       
  2416 void CFsSyncMessageScheduler::CompleteSessionRequests(CSessionFs* aSession, TInt aValue)
       
  2417 	{
       
  2418 	__PRINT2(_L("FsPluginManager::CompleteSessionRequests(%08x, %d)"), aSession, aValue);
       
  2419 	
       
  2420 	iLock.Wait();
       
  2421 	TDblQueIter<CFsRequest> q(iList);
       
  2422 	CFsRequest* pR;
       
  2423 	while((pR=q++)!=NULL)
       
  2424 		{
       
  2425 		if(pR->Session()==aSession)
       
  2426 			{
       
  2427 			pR->iLink.Deque();
       
  2428 			pR->Complete(aValue);
       
  2429 			}
       
  2430 		}
       
  2431 	iLock.Signal();
       
  2432 	}
       
  2433