If TECGetTextEncodingFromInternetName() requires a Pascal-style string, why is CopyCStringToPascal() discontinued in OSX 10.5?
It is my responsibility to build an old version of an open-source library for OSX 10.5. (The library is Xerces 2.8.)
The library fails to build out-of-the-box on OSX 10.5 due to (among other things) use of the discontinued OSX function CopyCStringToPascal()
. The relevant code snippet is:
Str255 pasEncodingName;
...
CopyCStringToPascal(cEncodingName, pasEncodingName);
TECGetTextEncodingFromInternetName (&textEncoding, pasEncodingName);
Investigation has shown that CopyCStringToPascal()
does, indeed, conv开发者_StackOverflowert a C string into a Pascal-style string (a string for which the first byte provides the number of characters in the string). Therefore, from context, it is clear that the second parameter to TECGetTextEncodingFromInternetName()
must be a Pascal-style string (although I cannot find this confirmed in any documentation from scavenging the internet).
Because the newest version of the open-source library (Xerces 3.1) successfully builds on OSX 10.5, and its implementation both explicitly defines the function CopyCStringToPascal()
(since it has been discontinued in OSX 10.5) to create a Pascal-style string, and continues to use TECGetTextEncodingFromInternetName()
(which has not been discontinued in OSX 10.5), I trust this to be confirmation that indeed TECGetTextEncodingFromInternetName()
continues to require a Pascal-style string even for OSX 10.5.
Because Pascal-style strings are STILL required by current OSX 10.5 system routines, I am mystified as to why the function CopyCStringToPascal()
, which converts to such a necessary Pascal string, has been discontinued in OSX 10.5. I'm writing this question in order to further confirm that I am not making a mistake by simply defining this function explicitly for Xerces 2.8 (and otherwise changing nothing in the area of the code relevant to this discussion) in order to get Xerces 2.8 to build with OSX 10.5. Thanks.
There are three upgrade paths, all through CFString.
The first, already suggested by Grady Player, is to use CFString to convert the encoding name to a Pascal string. You may be able to start with the encoding name in a CFString (using the CFSTR
macro); if not, you can create a CFString from the C string, and a Pascal string from the CFString.
The second is to use CFString, instead of Text Encoding Conversion Manager, to convert the encoding name to an encoding identifier. CFString and TEC both use the same identifiers (compare the constants between CFStringEncodingExt.h and TextCommon.h), so you can use CFStringConvertIANACharSetNameToEncoding
—which takes the encoding name as a CFString—to get the encoding identifier. If you pass the encoding identifier from CF to TEC, this is sort of cheating, but as long as Apple doesn't see fit to change all the constants for no apparent reason, it'll work.
The third is to use CFString for the conversion itself. Create a CFString from the input using CFStringCreateWithBytes
, and use CFStringGetBytes
to determine the output length and then again to perform the conversion. This solution drops TEC entirely.
While TEC itself isn't deprecated (yet), if it requires the use or reinvention of other APIs that have been deprecated/removed to make it work, that's also a bad sign for the longevity of your TEC-based code. I suggest filing a bug to ask for a modern replacement in TEC for TECGetTextEncodingFromInternetName
; you can decide what to do based on the response you get to your request.
if you just search CFString reference you see a few things that match Pascal, from what I can glean...
try
ConstStringPtr CFStringGetPascalStringPtr (
CFStringRef theString,
CFStringEncoding encoding
);
if that fails, use:
Boolean CFStringGetPascalString (
CFStringRef theString,
StringPtr buffer,
CFIndex bufferSize,
CFStringEncoding encoding
);
Also I don't see where it says you are supposed to use a pascal string.
encodingName
An Internet encoding name, in 7-bit US ASCII.
精彩评论