fbs/fontandbitmapserver/sfbs/FBSTOP.CPP
changeset 0 5d03bc08d59c
child 103 2717213c588a
child 163 bbf46f59e123
equal deleted inserted replaced
-1:000000000000 0:5d03bc08d59c
       
     1 // Copyright (c) 1995-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 //
       
    15 
       
    16 #include <hal.h>
       
    17 #include <gdi.h>
       
    18 #include <fntstore.h>
       
    19 #include <bitmap.h>
       
    20 #include <ecom/ecom.h>
       
    21 #include "fbsmessage.h"
       
    22 #include <graphics/bitmapuid.h>
       
    23 #include "SERVER.H"
       
    24 #include "BackGroundCompression.h"
       
    25 #include "BitwiseBitmap.inl"
       
    26 #include "bitmapconst.h"
       
    27 #include <graphics/openfontconstants.h>
       
    28 #include <graphics/openfontrasterizer.h>
       
    29 #include <graphics/gdi/glyphsample.h>
       
    30 
       
    31 // Local utility functions
       
    32 void ListImplementationsWithRetry(TUid& aInterfaceUid, RImplInfoPtrArray &aImplementationArray, TBool aRomOnly);
       
    33 
       
    34 
       
    35 CFbTop::CFbTop():
       
    36 	iDefaultLanguageForMetrics(ELangNone)
       
    37 	{
       
    38 	}
       
    39 
       
    40 CFbTop::~CFbTop()
       
    41 	{
       
    42 	if (iConIx)
       
    43 		{
       
    44 		iConIx->Remove(iBitmapCon);
       
    45 		iConIx->Remove(iFontCon);
       
    46 		}
       
    47 	// there are no bitmap objects left, so the background compression queue must be empty
       
    48 	delete iBackgroundCompression;
       
    49 	delete iMBMCache;
       
    50 	delete iFontStore;
       
    51 	iFilesys.Close();
       
    52 	iHeap->Check();
       
    53 	__RHEAP_MARKEND(iHeap);
       
    54 	delete iPile;
       
    55 	iHeap->Close();
       
    56 	iChunk.Close();
       
    57 	iLargeBitmapChunk.Close();
       
    58 	delete iConIx;
       
    59 #ifdef SYMBIAN_DEBUG_FBS_LOCKHEAP
       
    60 	iDebugMutex.Close();
       
    61 #endif
       
    62 	iFontNameAlias.ResetAndDestroy();
       
    63 	iBitmapObjectIndex.Reset();
       
    64 	REComSession::FinalClose();
       
    65 	}
       
    66 
       
    67 CFbTop* CFbTop::NewL()
       
    68 	{
       
    69 	CFbTop* pT=new(ELeave) CFbTop;
       
    70 	CleanupStack::PushL(pT);
       
    71 	pT->ConstructL();
       
    72 	CleanupStack::Pop();
       
    73 	return(pT);
       
    74 	}
       
    75 
       
    76 void CFbTop::ConstructL()
       
    77 	{
       
    78 	TInt maxmem = 0;
       
    79 	HAL::Get(HALData::EMemoryRAM, maxmem);
       
    80 	ASSERT(maxmem > 0);
       
    81 	TInt maxHeapSize = Min(maxmem, KFbServSharedHeapMaxSize);
       
    82 	
       
    83 	TChunkHeapCreateInfo sharedHeapCreateInfo(KFBSERVInitialHeapSize, maxHeapSize);
       
    84 	sharedHeapCreateInfo.SetCreateChunk(&KFBSERVSharedChunkName);
       
    85 	sharedHeapCreateInfo.SetSingleThread(EFalse);
       
    86 	sharedHeapCreateInfo.SetAlignment(0);
       
    87 	sharedHeapCreateInfo.SetGrowBy(KMinHeapGrowBy * KFBSERVHeapGrowByMultiplier);
       
    88 
       
    89 	if(KFbServWritableDataPagingMode == EFbsWdpPageBitmapDataAndSharedHeapChunksOnly)
       
    90 		{
       
    91 		//Request that the shared heap chunk is paged.
       
    92 		sharedHeapCreateInfo.SetPaging(TChunkHeapCreateInfo::EPaged);
       
    93 		}
       
    94 	else
       
    95 		{
       
    96 		//Use the creating process's paging attributes.
       
    97 		sharedHeapCreateInfo.SetPaging(TChunkHeapCreateInfo::EUnspecified);
       
    98 		}
       
    99 
       
   100 	iHeap = UserHeap::ChunkHeap(sharedHeapCreateInfo);
       
   101 	
       
   102 	User::LeaveIfError(iChunk.OpenGlobal(KFBSERVSharedChunkName,ETrue));
       
   103 	TInt virtualSize = CChunkPile::VirtualSize();
       
   104 	
       
   105 	TChunkCreateInfo createInfo;
       
   106 	createInfo.SetDisconnected(0, 0, virtualSize);
       
   107 	createInfo.SetGlobal(KFBSERVLargeChunkName);
       
   108 	createInfo.SetOwner(EOwnerProcess);
       
   109 	createInfo.SetClearByte(0xff); // clear to white on creation
       
   110 
       
   111 	if(KFbServWritableDataPagingMode == EFbsWdpPageBitmapDataChunkOnly || 
       
   112 		KFbServWritableDataPagingMode == EFbsWdpPageBitmapDataAndSharedHeapChunksOnly)
       
   113 		{
       
   114 		//Request that large bitmap chunk is paged.
       
   115 		createInfo.SetPaging(TChunkCreateInfo::EPaged);
       
   116 		}
       
   117 	else
       
   118 		{
       
   119 		//Use the creating process's paging attributes.
       
   120 		createInfo.SetPaging(TChunkCreateInfo::EUnspecified);
       
   121 		}
       
   122 
       
   123 	User::LeaveIfError(iLargeBitmapChunk.Create(createInfo));
       
   124 	__RHEAP_MARK(iHeap);
       
   125 	iConIx=CObjectConIx::NewL();
       
   126 	iBitmapCon=iConIx->CreateL();
       
   127 	iFontCon=iConIx->CreateL();
       
   128 	User::LeaveIfError(iFilesys.Connect());
       
   129 #ifdef SYMBIAN_DEBUG_FBS_LOCKHEAP
       
   130 	User::LeaveIfError(iDebugMutex.CreateGlobal(KFBSERVDebugMutexName));
       
   131 #endif
       
   132 	iPile = CChunkPile::NewL(iLargeBitmapChunk);
       
   133 	iFontStore=CFontStore::NewL(iHeap);
       
   134 	//Constructing a cache to store the stream ids of the bitmaps from a mbm file.
       
   135 	//The cache here will store maximum 30 bitmaps before  & maximum 30 after the 
       
   136 	//current loaded bitmap.These values are chosen as to optimize the boottime performance
       
   137 	//as we notice during the boottime logs,sequential loading of bitmaps never exceed 30 bitmaps.
       
   138 	// The cache will also store maximum 5 mbm files. This number must be as low as possible
       
   139 	// while trying to minimize flushing of the cache due to mbm file switching.
       
   140 	iMBMCache=new (ELeave) CFbTopStreamIdCache(30,30,5);
       
   141 
       
   142 	LoadOpenFontLibraries();
       
   143 	
       
   144 	iFontStore->LoadFontsAtStartupL();
       
   145 	LoadShaperFactories();
       
   146 
       
   147 	// start a new thread for background compression after all the other objects have been created
       
   148 	iBackgroundCompression = CFbsBackgroundCompression::NewL(*this);
       
   149 	}
       
   150 
       
   151 
       
   152 
       
   153 
       
   154 /*
       
   155 Load all ECOM implemented rasterizer DLLs.
       
   156 */
       
   157 
       
   158 void CFbTop::LoadOpenFontLibraries()
       
   159 	{
       
   160 	RImplInfoPtrArray implementationArray;
       
   161 	TUid uid = {KUidOpenFontRasterizerPlunginInterface};
       
   162 
       
   163 	// get implementation list
       
   164 	ListImplementationsWithRetry(uid, implementationArray, EFalse);
       
   165 
       
   166 	const TInt availCount = implementationArray.Count();
       
   167 	for (TInt count=0; count < availCount; ++count)
       
   168 		{
       
   169 		const CImplementationInformation* info = implementationArray[count];
       
   170 		// Create & install a rasterizer
       
   171 		// ignore Leaves, as any necessary cleanup will have already been done through the cleanup stack
       
   172 		TRAP_IGNORE(SafeInstallOfRasterizerL(info->ImplementationUid()));
       
   173 		}
       
   174 	
       
   175 	// free memory
       
   176 	implementationArray.ResetAndDestroy();
       
   177 	}
       
   178 
       
   179 
       
   180 /*
       
   181 Load all ECOM implemented shaper factory DLLs.
       
   182 */	
       
   183 void CFbTop::LoadShaperFactories()
       
   184 	{
       
   185 	RImplInfoPtrArray implementationArray;
       
   186 	TUid uid = {KUidShaperFactoryPlunginInterface};
       
   187 
       
   188 	// get implementation list
       
   189 	ListImplementationsWithRetry(uid, implementationArray, ETrue);
       
   190 
       
   191 	const TInt availCount = implementationArray.Count();
       
   192 	for (TInt count=0;count<availCount;++count)
       
   193 		{
       
   194 		const CImplementationInformation* info = implementationArray[count];
       
   195 		// Create & install a shaper factory
       
   196 		// ignore Leaves, as any necessary cleanup will have already been done through the cleanup stack
       
   197 		TRAP_IGNORE(SafeInstallOfShaperFactoryL(info->ImplementationUid()));
       
   198 		}
       
   199 
       
   200 	// free memory
       
   201 	implementationArray.ResetAndDestroy();
       
   202 	}
       
   203 
       
   204 
       
   205 void ListImplementationsWithRetry(TUid& aInterfaceUid, RImplInfoPtrArray &aImplementationArray, TBool aRomOnly)
       
   206 	{
       
   207 	// Making sure that no race situation arises between FBserv and Ecom
       
   208 	// If ECom is not ready, give it another chance and try again. if it still doesn't work 
       
   209 	// after the third try, then it just carries on quietly and fails... 
       
   210 	for (TInt ecomnotready =0; ecomnotready <3; ecomnotready++)
       
   211 		{
       
   212 		TInt ecomError = KErrNone;
       
   213 		if (aRomOnly)
       
   214 			{
       
   215 			TEComResolverParams resParams;
       
   216 			TRAP(ecomError, REComSession::ListImplementationsL(aInterfaceUid, resParams, KRomOnlyResolverUid, aImplementationArray));
       
   217 			}
       
   218 		else
       
   219 			{ // default resolver
       
   220 			TRAP(ecomError, REComSession::ListImplementationsL(aInterfaceUid, aImplementationArray));
       
   221 			}
       
   222 
       
   223 		if (!ecomError)
       
   224 			{
       
   225 			return;
       
   226 			}
       
   227 		else
       
   228 			{
       
   229 			User::After(0);
       
   230 			}
       
   231 		}
       
   232 	}
       
   233 
       
   234 // utility methods to transfer ownership, or destroy object on failure
       
   235 void CFbTop::SafeInstallOfRasterizerL(TUid aInterfaceImplUid)
       
   236 	{
       
   237 	COpenFontRasterizer* rasterizer = COpenFontRasterizer::NewL(aInterfaceImplUid);
       
   238 	CleanupStack::PushL(rasterizer);
       
   239 	// Install it in the font store.
       
   240 	iFontStore->InstallRasterizerL(rasterizer);
       
   241 	CleanupStack::Pop(rasterizer);
       
   242 	}
       
   243 
       
   244 
       
   245 void CFbTop::SafeInstallOfShaperFactoryL(TUid aInterfaceImplUid)
       
   246 	{
       
   247 	CShaperFactory* shaperFactory = CShaperFactory::NewL(aInterfaceImplUid);
       
   248 	CleanupStack::PushL(shaperFactory);
       
   249 	// Install it in the font store.
       
   250 	iFontStore->InstallShaperFactoryL(shaperFactory);
       
   251 	CleanupStack::Pop(shaperFactory);
       
   252 	}
       
   253 
       
   254 /**
       
   255 Gets the nearest matching font for a given font specification. If the named font cannot be found 
       
   256 font aliases are checked. 
       
   257 
       
   258 @param aFontObjPtr On success this contains the font object that is the closest match.
       
   259 @param aMessage The font request message.
       
   260 @param aFontSpec The font spec to match.
       
   261 @param aMaxHeight The maximum height of the font to match.
       
   262 @return KErrNone if successful, KErrNotFound if the font is not found, or one of the other System Error codes.
       
   263  */
       
   264 TInt CFbTop::GetNearestFont(
       
   265 	CFontObject*&		aFontObjPtr,
       
   266 	TFbsMessage			aMessage,
       
   267 	const TFontSpec&	aFontSpec,
       
   268 	TInt				aMaxHeight)
       
   269 	{
       
   270 #ifdef _DEBUG
       
   271 	User::Heap().Check();
       
   272 	iHeap->Check();
       
   273 #endif
       
   274 	aFontObjPtr = NULL;
       
   275 
       
   276 	TFontSpec fontSpec(aFontSpec);
       
   277 
       
   278 	// Check if the font typeface is empty and if so use the system default font if it is set
       
   279 	if (fontSpec.iTypeface.iName.Length() == 0 && iSystemDefaultFontTypefaceName.Length() != 0)
       
   280 		{
       
   281 		fontSpec.iTypeface.iName = iSystemDefaultFontTypefaceName;
       
   282 		}
       
   283 
       
   284 	if (GlyphSample::EScriptDefault == fontSpec.ScriptTypeForMetrics())
       
   285 		{
       
   286 		fontSpec.SetScriptTypeForMetrics(iDefaultLanguageForMetrics);
       
   287 		}
       
   288 
       
   289 	// Find the requested font
       
   290 	TBool familyNameExistsInTypefaceStore = iFontStore->HaveTypefaceFamilyName(fontSpec.iTypeface.iName);
       
   291 	
       
   292 	// If the font is not found try finding an alias font
       
   293 	if (!familyNameExistsInTypefaceStore) 
       
   294 		{
       
   295 		TInt aliasIndex = FindFontNameAlias(fontSpec.iTypeface.iName);
       
   296 		//KErrNotFound is the only error which can be returned
       
   297 		if (aliasIndex != KErrNotFound)
       
   298 			{
       
   299 			fontSpec.iTypeface.iName = *iFontNameAlias[aliasIndex + 1];
       
   300 			}
       
   301 		}
       
   302 
       
   303 	CFont* font = NULL;
       
   304 	TInt ret = GetNearestNonAliasedFont(font, aMessage, fontSpec, aMaxHeight);
       
   305 
       
   306 	if (ret != KErrNone)
       
   307 		{
       
   308 		return ret;
       
   309 		}
       
   310 
       
   311 	return CreateFontObjectFromFont(aFontObjPtr, font);
       
   312 	}
       
   313 	
       
   314 /**
       
   315 Gets the nearest matching loaded font for a given font specification.
       
   316 
       
   317 @param aFont On success this contains the font object that is the closest match.
       
   318 @param aMessage The font request message.
       
   319 @param aFontSpec The font spec to match.
       
   320 @param aMaxHeight The maximum height of the font to match.
       
   321 @return KErrNone if successful, KErrNotFound if the font is not found, or one of the other System Error codes.
       
   322 */
       
   323 TInt CFbTop::GetNearestNonAliasedFont(CFont*& aFont, TFbsMessage aMessage, const TFontSpec&	aFontSpec, TInt	aMaxHeight)
       
   324 	{
       
   325 	TInt ret = KErrNotSupported;
       
   326 	switch (aMessage)
       
   327 		{
       
   328 		case EFbsMessGetNearestFontToDesignHeightInTwips:
       
   329 			{
       
   330 			ret = iFontStore->GetNearestFontToDesignHeightInTwips(aFont, aFontSpec);
       
   331 			break;
       
   332 			}
       
   333 		case EFbsMessGetNearestFontToDesignHeightInPixels:
       
   334 			{
       
   335 			ret = iFontStore->GetNearestFontToDesignHeightInPixels(aFont, aFontSpec);
       
   336 			break;
       
   337 			}
       
   338 		case EFbsMessGetNearestFontToMaxHeightInTwips:
       
   339 			{
       
   340 			ret = iFontStore->GetNearestFontToMaxHeightInTwips(aFont, aFontSpec, aMaxHeight);
       
   341 			break;
       
   342 			}
       
   343 		case EFbsMessGetNearestFontToMaxHeightInPixels:
       
   344 			{
       
   345 			ret = iFontStore->GetNearestFontToMaxHeightInPixels(aFont, aFontSpec, aMaxHeight);
       
   346 			break;
       
   347 			}
       
   348 		}
       
   349 	return ret;
       
   350 	}
       
   351 
       
   352 TInt CFbTop::CreateFontObjectFromFont(CFontObject*& aFontObjPtr, CFont* aFont)
       
   353 	{
       
   354 	CFontObject* fontObjPtr = new CFontObject(iFontStore);
       
   355 	if (!fontObjPtr)
       
   356 		{
       
   357 		iFontStore->ReleaseFont(aFont);
       
   358 		return KErrNoMemory;
       
   359 		}
       
   360 	
       
   361 	fontObjPtr->iAddressPointer = reinterpret_cast<CBitmapFont*>(aFont);
       
   362 	fontObjPtr->iHeightInTwips = ((aFont->HeightInPixels() * iFontStore->iKPixelHeightInTwips) + 667) / 1000;
       
   363 	TRAPD(ret, iFontCon->AddL(fontObjPtr));
       
   364 	if (ret != KErrNone)
       
   365 		{
       
   366 		fontObjPtr->Close();
       
   367 		}
       
   368 	else
       
   369 		{ // transfer ownership
       
   370 		aFontObjPtr = fontObjPtr;
       
   371 		}
       
   372 	return ret;
       
   373 	}
       
   374 
       
   375 
       
   376 /** Create a Bitmap Font, from a UID and Algorithmic drawing Style see CFontStore::GetFontById()
       
   377 @internalComponent
       
   378 */
       
   379 TInt CFbTop::GetFontById(CFontObject*& aFontObjPtr,TUid aUid,const TAlgStyle& aAlgStyle)
       
   380 	{
       
   381 #ifdef _DEBUG
       
   382 	User::Heap().Check();
       
   383 	iHeap->Check();
       
   384 #endif
       
   385 	aFontObjPtr=NULL;
       
   386 	CBitmapFont* font=NULL;
       
   387 	TInt ret=iFontStore->GetFontById((CFont*&)font,aUid,(TAlgStyle&)aAlgStyle);
       
   388 	if (ret != KErrNone)
       
   389 		{
       
   390 		return ret;
       
   391 		}
       
   392 	return CreateFontObjectFromFont(aFontObjPtr, font);
       
   393 	}
       
   394 
       
   395 
       
   396 /** Create a bitmap with the given size, display mode and UID.
       
   397 
       
   398 @param aSize Size of the bitmap in pixels.
       
   399 @param aDispMode Display mode of the bitmap.
       
   400 @param aUid The UID to use for bitmap creation. This can be:
       
   401 	- KUidCFbsBitmapCreation for standard bitmaps.
       
   402 	- The application UID for hardware bitmaps.
       
   403 	- The data type UID for extended bitmaps.
       
   404 @param aReplacement If ETrue the bitmap is being created as a replacement
       
   405 	for a bitmap being made dirty by a resize or compress operation.
       
   406 @param aDataSize If different from zero, it indicates that the bitmap to create
       
   407 	is an extended bitmap and specifies the size in bytes of the bitmap.
       
   408 	If equal to zero, it indicates that the bitmap to create is a standard
       
   409 	bitmap or a hardware bitmap, depending on the value of aUid, and the size
       
   410 	in bytes is calculated from the size in pixels and the display mode.
       
   411 @internalComponent
       
   412 */
       
   413 CBitmapObject* CFbTop::CreateBitmapL(const TSize& aSize, TDisplayMode aDispMode, TUid aUid, TBool aReplacement, TInt aDataSize)
       
   414 	{
       
   415 #ifdef _DEBUG
       
   416 	User::Heap().Check();
       
   417 	iHeap->Check();
       
   418 #endif
       
   419 	CBitwiseBitmap* bmp=(CBitwiseBitmap*)iHeap->AllocL(sizeof(CBitwiseBitmap) + sizeof(CBitwiseBitmap::TExtra));
       
   420 	new(bmp) CBitwiseBitmap(iHeap,iPile);
       
   421 	CleanupDeletePushL(bmp);  // CBitwiseBitmap is not derived from CBase!
       
   422 
       
   423 	if (aDataSize == 0)
       
   424 		User::LeaveIfError(bmp->Construct(aSize, aDispMode, aUid));
       
   425 	else
       
   426 		User::LeaveIfError(bmp->ConstructExtended(aSize, aDispMode, aUid, aDataSize));
       
   427 	// bmp popped out of the clean-up stack by NewL
       
   428 	CBitmapObject* bmpObj = CBitmapObject::NewL(*this, bmp, aReplacement);
       
   429 	if (!aReplacement)
       
   430 		{
       
   431 		bmp->Extra()->iSerialNumber = iNextAvailableSerialNumber++;
       
   432 		}
       
   433 
       
   434 	return bmpObj;
       
   435 	}
       
   436 
       
   437 CBitmapObject* CFbTop::LoadBitmapL(const TDesC& aFilename, TInt32 aId, TUint aFileOffset, RFile* aFile, TInt aSessionHandle)
       
   438 	{
       
   439 	CBitwiseBitmap* bmp=DoLoadBitmapLC(aFilename, aId, aFileOffset, aFile, aSessionHandle);
       
   440 	// bmp popped out of the clean-up stack by NewL
       
   441 	CBitmapObject* bmpObj = CBitmapObject::NewL(*this, bmp, EFalse);
       
   442 
       
   443 	return bmpObj;
       
   444 	}
       
   445 
       
   446 _LIT(KZDrive, "z:");
       
   447 
       
   448 CBitwiseBitmap* CFbTop::DoLoadBitmapLC(const TDesC& aFilename, TInt32 aId, TUint aFileOffset, RFile* aFile, TInt aSessionHandle)
       
   449 	{
       
   450 #ifdef _DEBUG
       
   451 	User::Heap().Check();
       
   452 	iHeap->Check();
       
   453 #endif
       
   454 	CBitwiseBitmap* bmp=(CBitwiseBitmap*)iHeap->AllocL(sizeof(CBitwiseBitmap) + sizeof(CBitwiseBitmap::TExtra));
       
   455 	new(bmp) CBitwiseBitmap(iHeap,iPile);
       
   456 	bmp->Extra()->iSerialNumber = iNextAvailableSerialNumber++;
       
   457 	CleanupDeletePushL(bmp);  // CBitwiseBitmap is not derived from CBase!
       
   458 
       
   459 	if (NULL == aFile)
       
   460 		{
       
   461 		// In this case file should be in z: drive
       
   462 		// so load the bitmap from the mbm cache
       
   463 		TStreamId streamid(0);
       
   464 		streamid=iMBMCache->GetStreamIdL(iFilesys,aFilename,aId,aFileOffset,aSessionHandle);
       
   465 		bmp->ConstructL(iMBMCache->MruFileStore(),streamid);
       
   466 		}
       
   467 	else
       
   468 		{
       
   469 		//only use the cache when it is Rom File which is read only because when using
       
   470 		//the cache the file store is always opened as read access until it is replaced by
       
   471 		//another different file, Trying to write it(RAM file) will cause access violation
       
   472 		//and therefore we have to split the implementation into two parts one for ROM
       
   473 		//and one for RAM
       
   474 		if (aFilename.Left(2).CompareF(KZDrive))
       
   475 			{
       
   476 			// File is not in ROFS
       
   477 			bmp->ConstructL(*aFile,aId,aFileOffset);
       
   478 			}
       
   479 		else
       
   480 			{
       
   481 			// File is in ROFS
       
   482 			TStreamId streamid(0);
       
   483 			streamid=iMBMCache->GetStreamIdL(*aFile,aFilename,aId,aFileOffset,aSessionHandle);
       
   484 
       
   485 			bmp->ConstructL(iMBMCache->MruFileStore(),streamid);
       
   486 			}
       
   487 		}
       
   488 	return bmp;
       
   489 	}
       
   490 
       
   491 
       
   492 /* Similar to LoadBitmap.
       
   493 This function only performs a load the first time it is called for a
       
   494 particular bitmap.  Subsequent calls increment a reference counting object.
       
   495 
       
   496 Upon return, aBmpObjPtr points to an object containing a pointer to the loaded bitmap.
       
   497 */
       
   498 CSharedBitmapObject* CFbTop::ShareBitmapL(TDes& aFilename, TInt32 aId, TUint aFileOffset, RFile* aFile, TInt aSessionHandle)
       
   499 	{
       
   500 	TTime modtime(0);
       
   501 	if (aFilename.Left(2).CompareF(KZDrive))// instead of Compare, CompareF is used to perform folding prior to Compare which is safe with Unicode.
       
   502 		{
       
   503 		// file is not in z: drive so it should not be null.
       
   504 		__ASSERT_DEBUG(aFile != NULL, User::Panic(KFBSERVPanicCategory, KErrBadHandle));
       
   505 		// File is not in ROM so ModTime is needed to identify it
       
   506 		User::LeaveIfError(aFile->Modified(modtime));
       
   507 		}
       
   508 
       
   509 	// Creation of the key is performed here so that it can potentially be
       
   510 	// reused in both object lookup and object creation
       
   511 	HBufC* key = CSharedBitmapObject::KeyLC(aFilename, aId, modtime);
       
   512 
       
   513 	// Calculation of the hash value is performed here so that it can 
       
   514 	// potentially be reused in both object lookup and object insert.
       
   515 	const TUint hash = iSharedBitmapObjectHashMap.Hash(*key);    
       
   516 
       
   517 	CSharedBitmapObject* bmpObj = iSharedBitmapObjectHashMap.Lookup(*key, hash);
       
   518 	
       
   519 	if (bmpObj)
       
   520 		{
       
   521 		// Bitmap already in memory
       
   522 		CleanupStack::PopAndDestroy(key);      // key will not be needed
       
   523 		User::LeaveIfError(bmpObj->Open());    // increase reference count
       
   524 		}
       
   525 	else
       
   526 		{
       
   527 		// Bitmap not in memory
       
   528 		CBitwiseBitmap* bmp = DoLoadBitmapLC(aFilename, aId, aFileOffset, aFile, aSessionHandle);
       
   529 		// bmp and key popped out of the clean-up stack by NewL
       
   530 		bmpObj = CSharedBitmapObject::NewL(*this, bmp, key, hash);
       
   531 		}
       
   532 
       
   533 	return bmpObj;
       
   534 	}
       
   535 
       
   536 TInt CFbTop::GetCleanBitmap(CBitmapObject*& aBmpObjPtr)
       
   537 	{
       
   538 	while (aBmpObjPtr->CleanBitmap() != NULL)
       
   539 		{
       
   540 		aBmpObjPtr = aBmpObjPtr->CleanBitmap();
       
   541 		}
       
   542 	if (aBmpObjPtr->IsInCompressionQueue())
       
   543 		return KErrInUse;
       
   544 	return KErrNone;
       
   545 	}
       
   546 
       
   547 CBitmapObject* CFbTop::FindBitmap(TInt aHandle)
       
   548 	{
       
   549 	TInt index = iBitmapObjectIndex.FindInOrder(aHandle, CBitmapObject::Compare);
       
   550 	if (index != KErrNotFound)
       
   551 		return iBitmapObjectIndex[index];
       
   552 	return NULL;
       
   553 	}
       
   554 
       
   555 TBool CFbTop::ValidFontHandle(TInt aHandle)
       
   556 	{
       
   557 	TInt limit=iFontCon->Count();
       
   558 	for(TInt count=0;count<limit;count++)
       
   559 		if(aHandle==(TInt)((*iFontCon)[count]))
       
   560 			return(ETrue);
       
   561 	return(EFalse);
       
   562 	}
       
   563 	
       
   564 TBool CFbTop::ValidBitmapFont(TInt aHandle)
       
   565 	{
       
   566 	TInt limit=iFontCon->Count();
       
   567 	for(TInt count=0;count<limit;count++)
       
   568 		{
       
   569 		CFontObject* fontObjPtr = reinterpret_cast<CFontObject*>((*iFontCon)[count]);
       
   570 		if(aHandle==(TInt)(fontObjPtr->iAddressPointer))
       
   571 			return(ETrue);
       
   572 		}
       
   573 	return(EFalse);
       
   574 	}
       
   575 
       
   576 CFontStore* CFbTop::FontStore() const
       
   577 	{
       
   578 	return(iFontStore);
       
   579 	}
       
   580 
       
   581 RHeap* CFbTop::Heap() const
       
   582 	{
       
   583 	return(iHeap);
       
   584 	}
       
   585 
       
   586 CChunkPile* CFbTop::Pile() const
       
   587 	{
       
   588 	return(iPile);
       
   589 	}
       
   590 
       
   591 TInt CFbTop::HeapBase() const
       
   592 	{
       
   593 	return(TInt(iChunk.Base()));
       
   594 	}
       
   595 
       
   596 void CFbTop::SetFontNameAliasL(const RMessage2& aMessage)
       
   597 	{
       
   598 	const TInt aliasNameLength = aMessage.Int1();
       
   599 	if (aliasNameLength <= 0)
       
   600 		return; // No alias name to set
       
   601 	
       
   602 	if(aliasNameLength * sizeof(TText) * 2 >= KMaxTInt)
       
   603 		{
       
   604 		aMessage.Panic(KFBSERVPanicCategory,KErrArgument);
       
   605 		return;
       
   606 		}
       
   607 		
       
   608 	HBufC* aliasName = HBufC::NewMaxLC(aliasNameLength);
       
   609 	TPtr aliasNamePtr(aliasName->Des());
       
   610 	aMessage.ReadL(0,aliasNamePtr);
       
   611 
       
   612 	const TInt aliasIndex = FindFontNameAlias(*aliasName);
       
   613 
       
   614 	const TInt fontNameLength = aMessage.Int3();
       
   615 
       
   616 	if (fontNameLength > 0)
       
   617 		{ // Set or change an alias
       
   618 		HBufC* fontName = HBufC::NewMaxLC(fontNameLength);
       
   619 		TPtr fontNamePtr(fontName->Des());
       
   620 		aMessage.ReadL(2,fontNamePtr);
       
   621 
       
   622 		if (aliasIndex != KErrNotFound)
       
   623 			{ // Change an existing alias
       
   624 			delete iFontNameAlias[aliasIndex + 1];
       
   625 			iFontNameAlias[aliasIndex + 1] = fontName;
       
   626 
       
   627 			CleanupStack::Pop(); // fontName
       
   628 			CleanupStack::PopAndDestroy(); // aliasName
       
   629 			}
       
   630 		else
       
   631 			{ // Set a new alias
       
   632 			User::LeaveIfError(iFontNameAlias.Append(aliasName));
       
   633 			TInt ret = iFontNameAlias.Append(fontName);
       
   634 			if (ret != KErrNone)
       
   635 				{
       
   636 				iFontNameAlias.Remove(iFontNameAlias.Count() - 1);
       
   637 				User::Leave(ret);
       
   638 				}
       
   639 
       
   640 			CleanupStack::Pop(); // fontName
       
   641 			CleanupStack::Pop(); // aliasName
       
   642 			}
       
   643 		}
       
   644 	else
       
   645 		{ // No fontName so delete the alias
       
   646 		CleanupStack::PopAndDestroy(); // aliasName
       
   647 		if (aliasIndex != KErrNotFound)
       
   648 			{
       
   649 			delete iFontNameAlias[aliasIndex];
       
   650 			iFontNameAlias.Remove(aliasIndex);
       
   651 			delete iFontNameAlias[aliasIndex];
       
   652 			iFontNameAlias.Remove(aliasIndex);
       
   653 			}
       
   654 		}
       
   655 	}
       
   656 
       
   657 TInt CFbTop::FindFontNameAlias(const TDesC& aAlias)
       
   658 	{
       
   659 	const TInt fontNameAliasCount = iFontNameAlias.Count();
       
   660 
       
   661 	for (TInt index = 0; index < fontNameAliasCount; index += 2)
       
   662 		{
       
   663 		if ((*iFontNameAlias[index]).CompareF(aAlias)==0)
       
   664 			{
       
   665 			return index;
       
   666 			}
       
   667 		}
       
   668 
       
   669 	return KErrNotFound;
       
   670 	}
       
   671 
       
   672 void CFbTop::SetDefaultLanguageForMetrics(const RMessage2& aMessage)
       
   673 	{
       
   674 	iDefaultLanguageForMetrics = static_cast<TLanguage>(aMessage.Int0());
       
   675 	}
       
   676 
       
   677 void CFbTop::CloseFileStores(TInt aSessionHandle)
       
   678 	{
       
   679 	iMBMCache->CloseFileStores(aSessionHandle);
       
   680 	}
       
   681 
       
   682 void CFbTop::SetSystemDefaultTypefaceName(const TDesC& aFontTypefaceName)
       
   683 	{
       
   684 	iSystemDefaultFontTypefaceName = aFontTypefaceName;
       
   685 	}
       
   686 
       
   687 TInt CFbTop::GetAllBitmapHandles(const RMessage2& aMessage) const
       
   688 	{
       
   689 	TPckgBuf<TInt> handleBuffer; // Use this buffer to store the bitmap handles to write to the message buffer
       
   690 	const TInt numBitmaps = iBitmapObjectIndex.Count();
       
   691 	TInt ret = KErrNone;
       
   692 	for (TInt count=0; count<numBitmaps; ++count)
       
   693 		{
       
   694 		handleBuffer() = iBitmapObjectIndex[count]->Handle();
       
   695 		ret = aMessage.Write(0, handleBuffer, KNumBytesPerBitmapHandle * count);
       
   696 		if (ret!=KErrNone)
       
   697 			break;
       
   698 		}	
       
   699 	return ret;
       
   700 	}
       
   701 
       
   702 void CFbTop::AddClientHelper(TFbClientHelper& aHelper)
       
   703 	{
       
   704 	iClientHelpers.AddLast(aHelper);
       
   705 	}
       
   706 
       
   707 void CFbTop::NotifyDirtyBitmap(CBitmapObject& aBmpObj, CFbClient* aClient)
       
   708 	{
       
   709 	TDblQueIter<TFbClientHelper> iterator(iClientHelpers);
       
   710 	TFbClientHelper* helper;
       
   711 	while ((helper = iterator++) != NULL)
       
   712 		{
       
   713 		if (aClient != &helper->iClient)
       
   714 			helper->iClient.NotifyDirtyBitmap(aBmpObj);
       
   715 		}
       
   716 	}
       
   717 
       
   718 TInt CFbTop::BitmapConUniqueID() const
       
   719 	{
       
   720 	return iBitmapCon->UniqueID();
       
   721 	}
       
   722 
       
   723 TInt CFbTop::FontConUniqueID() const
       
   724 	{
       
   725 	return iFontCon->UniqueID();
       
   726 	}