/* File: DoubleByteBassCache.c Contains: Support routines for double byte modifications to the TrueType cache. Written by: John Farmer Copyright: © 1990-1992 by Apple Computer, Inc., all rights reserved. Change History (most recent first): <2> 1/3/92 JSM Roll-in changes from Sakura: When shrinking cache, add Glyph header size to new cache size. Fix AllocateEntrySpaceInCurrentCache() so heap isnŐt trashed. System 6.1.0 Changes: <2> 7/01/91 jlf Removed incorrect header documentation. <1> 1/09/90 jlf Created file. */ // Include Statements #include "Errors.h" #include "Fonts.h" #include "Memory.h" #include "Script.h" #include "Types.h" #include "FSCdefs.h" #include "FontScaler.h" #include "PartialFontExtensions.h" #include "Bass_Cache.h" #include "DoubleByteBassCache.h" /* -------------------------------------------------------------------------------------- Routine: error = AllocateEntrySpaceInCurrentCache( entrySize, splineKey ) Purpose: Warnings: ----------------------------------------------------------------------------------- */ OSErr AllocateEntrySpaceInCurrentCache( Size entrySize, sb_SplineKeyHdl splineKey ) { // Locals OSErr error; uint16 cachePlace; Size oldCacheSize, newCacheSize; sb_CacheHeadHdl cacheHandle, newCacheHandle; THz cacheZone; error = noErr; cacheHandle = (*splineKey)->cacheHand; oldCacheSize = GetHandleSize( (Handle) cacheHandle ); // add GLYPH_HEAD_BYTES so heap isn't trashed newCacheSize = (*cacheHandle)->addEntryOffset + entrySize + GLYPH_HEAD_BYTES; if ( newCacheSize > oldCacheSize ) { cacheZone = (*splineKey)->cacheZone; cachePlace = (*splineKey)->cachePlace; newCacheHandle = (sb_CacheHeadHdl) sb_SizeTheBlock( splineKey, (Handle) cacheHandle, &cacheZone, newCacheSize, kKeepContents, cachePlace, noShrink ); if ( newCacheHandle != nil ) { (*splineKey)->cacheHand = newCacheHandle; (*splineKey)->cacheZone = cacheZone; } else { error = sb_ShrinkCacheToMin( cacheHandle, 0 ); if ( error == noErr ) { newCacheSize = (*cacheHandle)->addEntryOffset + entrySize + GLYPH_HEAD_BYTES; newCacheHandle = (sb_CacheHeadHdl) sb_SizeTheBlock( splineKey, (Handle) cacheHandle, &cacheZone, newCacheSize, kKeepContents, cachePlace, noShrink ); if ( newCacheHandle == nil ) { error = memFullErr; } else { (*splineKey)->cacheHand = newCacheHandle; (*splineKey)->cacheZone = cacheZone; } } } } return( error ); } /* -------------------------------------------------------------------------------------- Routine: error = AddLowByteGlyphOffsetTable( glyphID, splineKey ) Purpose: Warnings: change entry in sb_glyph. ----------------------------------------------------------------------------------- */ OSErr AddLowByteGlyphOffsetTable( uint16 glyphID, sb_SplineKeyHdl splineKey ) { // Locals unsigned char lowByte, highByte; uint16 lowByteOffsetIndex; uint32 *lowByteGlyphOffsetTablePointer; OSErr error; EncodingTablePointer encodingPointer; sb_CacheHeadHdl cacheHandle; error = noErr; highByte = (glyphID >> 8); lowByte = (glyphID & 0x00FF); cacheHandle = (*splineKey)->cacheHand; encodingPointer = (EncodingTablePointer) (*cacheHandle)->fEncodingTablePointer; if ( (encodingPointer != nil) && (lowByte != 0) ) { if ( (encodingPointer->fHighByte[highByte] != kSingleByte) && ((*cacheHandle)->glyphArray[highByte] == 0) ) { error = AllocateEntrySpaceInCurrentCache( kLowByteGlyphOffsetTableSize, splineKey ); if ( error == noErr ) { cacheHandle = (*splineKey)->cacheHand; lowByteGlyphOffsetTablePointer = (uint32*) ((Ptr) *cacheHandle + (*cacheHandle)->addEntryOffset); for ( lowByteOffsetIndex = 0; lowByteOffsetIndex <= 255; lowByteOffsetIndex++ ) lowByteGlyphOffsetTablePointer[lowByteOffsetIndex] = 0; (*cacheHandle)->glyphArray[highByte] = (*cacheHandle)->addEntryOffset; (*cacheHandle)->addEntryOffset += kLowByteGlyphOffsetTableSize; } } } return( error ); } /* -------------------------------------------------------------------------------------- Routine: cacheOffset = GetSingleOrDoubleByteGlyphEntryOffset( glyphID, cacheHandle ) Purpose: Warnings: ----------------------------------------------------------------------------------- */ uint32 GetSingleOrDoubleByteGlyphEntryOffset( uint16 glyphID, sb_CacheHeadPtr cachePointer ) { // Locals unsigned char highByte, lowByte; uint32 lowByteTableOffset, *glyphEntryPointer; EncodingTablePointer encodingPointer; highByte = (glyphID >> 8); lowByte = (glyphID & 0x00FF); glyphEntryPointer = &cachePointer->glyphArray[0]; encodingPointer = (EncodingTablePointer) cachePointer->fEncodingTablePointer; if ( encodingPointer == nil ) { glyphEntryPointer = &cachePointer->glyphArray[lowByte]; } else if ( lowByte == 0 ) { if ( encodingPointer->fHighByte[highByte] == kSingleByte ) { glyphEntryPointer = &cachePointer->glyphArray[highByte]; } } else { if ( (encodingPointer->fHighByte[highByte] != kSingleByte) && (encodingPointer->fLowByte[lowByte] != kSingleByte) ) { lowByteTableOffset = cachePointer->glyphArray[highByte] & ENTRY_MASK; if ( lowByteTableOffset != 0 ) { glyphEntryPointer = (uint32*) ((Ptr) cachePointer + lowByteTableOffset) + lowByte; } } } return( (Ptr) glyphEntryPointer - (Ptr) cachePointer ); }