tweak xml parsing to not ignore white space

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@35533 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
Richard Frith-MacDonald 2012-09-06 12:58:25 +00:00
parent b099149311
commit e46b8d3567
2 changed files with 211 additions and 251 deletions

148
ChangeLog
View file

@ -1,3 +1,9 @@
2012-09-06 Richard Frith-Macdonald <rfm@gnu.org>
* Source/NSPropertyList.m:
Don't ignore whitespace in keys and values when parsing XML ... the
DTD says everything apart from array and dict contains #PCDATA.
2012-09-05 Richard Frith-Macdonald <rfm@gnu.org> 2012-09-05 Richard Frith-Macdonald <rfm@gnu.org>
* Source/NSScanner.m: Compatibility tweak reported by hns@computer.org * Source/NSScanner.m: Compatibility tweak reported by hns@computer.org
@ -11,38 +17,38 @@
2012-09-03 Richard Frith-Macdonald <rfm@gnu.org> 2012-09-03 Richard Frith-Macdonald <rfm@gnu.org>
* Source\NSTimeZone.m: * Source/NSTimeZone.m:
* Source\NSBundle.m: * Source/NSBundle.m:
* Source\NSPropertyList.m: * Source/NSPropertyList.m:
* Source\NSProcessInfo.m: * Source/NSProcessInfo.m:
* Source\NSSocketPort.m: * Source/NSSocketPort.m:
* Source\NSRunLoop.m: * Source/NSRunLoop.m:
* Source\NSMessagePortNameServer.m: * Source/NSMessagePortNameServer.m:
* Source\NSDistributedLock.m: * Source/NSDistributedLock.m:
* Source\GSHTTPURLHandle.m: * Source/GSHTTPURLHandle.m:
* Source\NSZone.m: * Source/NSZone.m:
* Source\NSPage.m: * Source/NSPage.m:
* Source\NSMessagePort.m: * Source/NSMessagePort.m:
* Source\NSUnarchiver.m: * Source/NSUnarchiver.m:
* Source\win32\GSFileHandle.m: * Source/win32/GSFileHandle.m:
* Source\NSFileManager.m: * Source/NSFileManager.m:
* Source\common.h: * Source/common.h:
* Source\NSString.m: * Source/NSString.m:
* Source\Additions\NSData+GNUstepBase.m: * Source/Additions/NSData+GNUstepBase.m:
* Source\Additions\Unicode.m: * Source/Additions/Unicode.m:
* Source\Additions\NSMutableString+GNUstepBase.m: * Source/Additions/NSMutableString+GNUstepBase.m:
* Source\Additions\NSError+GNUstepBase.m: * Source/Additions/NSError+GNUstepBase.m:
* Source\Additions\GSMime.m: * Source/Additions/GSMime.m:
* Source\Additions\NSString+GNUstepBase.m: * Source/Additions/NSString+GNUstepBase.m:
* Source\Additions\GCArray.m: * Source/Additions/GCArray.m:
* Source\Additions\GSXML.m: * Source/Additions/GSXML.m:
* Source\Additions\NSNumber+GNUstepBase.m: * Source/Additions/NSNumber+GNUstepBase.m:
* Source\Additions\GSObjCRuntime.m: * Source/Additions/GSObjCRuntime.m:
* Source\GSString.m: * Source/GSString.m:
* Source\NSObjCRuntime.m: * Source/NSObjCRuntime.m:
* Source\GSFormat.m: * Source/GSFormat.m:
* Source\GSFileHandle.m: * Source/GSFileHandle.m:
* Source\NSTask.m: * Source/NSTask.m:
On windows with mingw we can use strtoull() rather than _strtoui64(). On windows with mingw we can use strtoull() rather than _strtoui64().
Also, remove redundant header includes since string.h is in common.h Also, remove redundant header includes since string.h is in common.h
@ -3239,8 +3245,8 @@
* Source/NSBundle.m: ([+initialize]) change to use 'right' path * Source/NSBundle.m: ([+initialize]) change to use 'right' path
handling so that our core paths are established correctly even if handling so that our core paths are established correctly even if
an app has set the wrong path handling mode for the currenty platform. an app has set the wrong path handling mode for the currenty platform.
* Tests\base\NSURL\basic.m: * Tests/base/NSURL/basic.m:
* Tests\base\NSString\test02.m: * Tests/base/NSString/test02.m:
Fix path portability bugs in tests. Fix path portability bugs in tests.
2011-04-03 Richard Frith-Macdonald <rfm@gnu.org> 2011-04-03 Richard Frith-Macdonald <rfm@gnu.org>
@ -3850,24 +3856,24 @@
2011-02-23 Richard Frith-Macdonald <rfm@gnu.org> 2011-02-23 Richard Frith-Macdonald <rfm@gnu.org>
* Source\NSCalendarDate.m: * Source/NSCalendarDate.m:
* Source\NSArray.m: * Source/NSArray.m:
* Source\NSDebug.m: * Source/NSDebug.m:
* Source\NSCalendar.m: * Source/NSCalendar.m:
* Source\NSURLResponse.m: * Source/NSURLResponse.m:
* Source\NSObject.m: * Source/NSObject.m:
* Source\NSDecimalNumber.m: * Source/NSDecimalNumber.m:
* Source\Additions\GSMime.m: * Source/Additions/GSMime.m:
* Source\NSDateFormatter.m: * Source/NSDateFormatter.m:
* Source\NSDate.m: * Source/NSDate.m:
* Source\NSDictionary.m: * Source/NSDictionary.m:
* Source\NSSet.m: * Source/NSSet.m:
* Headers\Foundation\NSCalendarDate.h: * Headers/Foundation/NSCalendarDate.h:
* Headers\Foundation\NSDecimalNumber.h: * Headers/Foundation/NSDecimalNumber.h:
* Headers\Foundation\NSDate.h: * Headers/Foundation/NSDate.h:
* Headers\Foundation\NSArray.h: * Headers/Foundation/NSArray.h:
* Headers\Foundation\NSDictionary.h: * Headers/Foundation/NSDictionary.h:
* Headers\Foundation\NSSet.h: * Headers/Foundation/NSSet.h:
Tweaks to avoid compiler warnings on mingw and to make the Tweaks to avoid compiler warnings on mingw and to make the
-descriptionWithLocale: method consistently take an id argument -descriptionWithLocale: method consistently take an id argument
as it now does on OSX. as it now does on OSX.
@ -5587,7 +5593,7 @@
* Tools/AGSParser.h: * Tools/AGSParser.h:
* Tools/AGSParser.m: * Tools/AGSParser.m:
(-canWrapWithParagraphMarkup:, -generateParagraphMarkupForString:): (-canWrapWithParagraphMarkup:, -generateParagraphMarkupForString:):
Tweaked paragraph generation to ignore \n\n sequences inside <example> Tweaked paragraph generation to ignore /n/n sequences inside <example>
markup. markup.
(-parseDeclaration): Added enum documentation parsing. (-parseDeclaration): Added enum documentation parsing.
@ -5653,7 +5659,7 @@
* Tools/autogsdoc.m: * Tools/autogsdoc.m:
* Tools/AGSParser.m: * Tools/AGSParser.m:
Added the ability to generate paragraph markup. Turned off by default. Added the ability to generate paragraph markup. Turned off by default.
For each paragraph break ('\n\n' sequence) and when no incompatible For each paragraph break ('/n/n' sequence) and when no incompatible
elements exist in the scanned paragraph, <p> tags can be automatically elements exist in the scanned paragraph, <p> tags can be automatically
inserted (more explanations in -canWrapWithParagraphMarkup: doc). inserted (more explanations in -canWrapWithParagraphMarkup: doc).
@ -6280,7 +6286,7 @@
2010-04-07 Doug Simons <doug.simons@testplant.com> 2010-04-07 Doug Simons <doug.simons@testplant.com>
* Source/NSPathUtilities.m: Prefer USERPROFILE for the * Source/NSPathUtilities.m: Prefer USERPROFILE for the
NSHomeDirectory() on Windows if HOMEPATH is set to '\'. NSHomeDirectory() on Windows if HOMEPATH is set to '/'.
2010-04-07 Richard Frith-Macdonald <rfm@gnu.org> 2010-04-07 Richard Frith-Macdonald <rfm@gnu.org>
@ -7457,7 +7463,7 @@
* Source/NSPropertyList.m: Revert last change, which broke XML * Source/NSPropertyList.m: Revert last change, which broke XML
generation by placing illegal character entities in the output. generation by placing illegal character entities in the output.
Fix menu position problem by adding missing code to unescape Fix menu position problem by adding missing code to unescape
the \U escapes we put in the output when we read back in again. the /U escapes we put in the output when we read back in again.
NB. should check that we use character entities for all legal NB. should check that we use character entities for all legal
characters and only use the escape mechanism for *really* illegal characters and only use the escape mechanism for *really* illegal
ones (such as the menu location key). ones (such as the menu location key).
@ -7632,13 +7638,13 @@
2009-09-27 Richard Frith-Macdonald <rfm@gnu.org> 2009-09-27 Richard Frith-Macdonald <rfm@gnu.org>
* Source\win32\GSFileHandle.m: * Source/win32/GSFileHandle.m:
* Source\win32\NSMessagePort.m: * Source/win32/NSMessagePort.m:
* Source\win32\GSRunLoopCtxt.m: * Source/win32/GSRunLoopCtxt.m:
* Source\win32\NSStream.m: * Source/win32/NSStream.m:
* Source\win32\NSMessagePortNameServer.m: * Source/win32/NSMessagePortNameServer.m:
* Source\NSPipe.m: * Source/NSPipe.m:
* Source\NSTask.m: * Source/NSTask.m:
Fixes to try and improve subtask handling on windows. Fixes to try and improve subtask handling on windows.
1. change scheme to create all handles as not inheritable, and 1. change scheme to create all handles as not inheritable, and
just make the handles we want the child to have inheritable while just make the handles we want the child to have inheritable while
@ -8236,7 +8242,7 @@
2009-05-16 Richard Frith-Macdonald <rfm@gnu.org> 2009-05-16 Richard Frith-Macdonald <rfm@gnu.org>
* Source/NSURL.m: Add support for file URLs on mswindows. The path * Source/NSURL.m: Add support for file URLs on mswindows. The path
may be of the form C:\... rather than /... (and the colon might be may be of the form C:/... rather than /... (and the colon might be
a vertical bar). a vertical bar).
Also makefile fixes for bug #26446 Also makefile fixes for bug #26446
@ -8484,13 +8490,13 @@
2009-03-18 Richard Frith-Macdonald <rfm@gnu.org> 2009-03-18 Richard Frith-Macdonald <rfm@gnu.org>
* Source\win32\GSFileHandle.m: * Source/win32/GSFileHandle.m:
* Source\win32\NSMessagePort.m: * Source/win32/NSMessagePort.m:
* Source\win32\NSMessagePortNameServer.m: * Source/win32/NSMessagePortNameServer.m:
* Source\NSConcreteMapTable.m: * Source/NSConcreteMapTable.m:
* Source\Additions\GSCompatibility.m: * Source/Additions/GSCompatibility.m:
* Source\Additions\GSCategories.m: * Source/Additions/GSCategories.m:
* Source\NSData.m: * Source/NSData.m:
Fixes for windows and changes to GC code, plus changes for old Fixes for windows and changes to GC code, plus changes for old
compilers which don't support anonymous unions, plus improvement compilers which don't support anonymous unions, plus improvement
to error reporting on windows, plus fix to correctly rename to error reporting on windows, plus fix to correctly rename

View file

@ -88,7 +88,7 @@ extern BOOL GSScanDouble(unichar*, unsigned, double*);
id key; id key;
BOOL inArray; BOOL inArray;
BOOL inDictionary; BOOL inDictionary;
BOOL inString; BOOL inPCData;
BOOL parsed; BOOL parsed;
BOOL success; BOOL success;
id plist; id plist;
@ -143,7 +143,7 @@ extern BOOL GSScanDouble(unichar*, unsigned, double*);
- (void) parser: (NSXMLParser *)parser - (void) parser: (NSXMLParser *)parser
foundCharacters: (NSString *)string foundCharacters: (NSString *)string
{ {
if (YES == inString) if (YES == inPCData)
{ {
[value appendString: string]; [value appendString: string];
} }
@ -156,7 +156,7 @@ foundCharacters: (NSString *)string
- (void) parser: (NSXMLParser *)parser - (void) parser: (NSXMLParser *)parser
foundIgnorableWhitespace: (NSString *)string foundIgnorableWhitespace: (NSString *)string
{ {
if (YES == inString) if (YES == inPCData)
{ {
[value appendString: string]; [value appendString: string];
} }
@ -200,9 +200,9 @@ foundIgnorableWhitespace: (NSString *)string
inArray = YES; inArray = YES;
inDictionary = NO; inDictionary = NO;
} }
else if ([elementName isEqualToString: @"string"] == YES) else
{ {
inString = YES; inPCData = YES;
} }
} }
@ -213,7 +213,7 @@ foundIgnorableWhitespace: (NSString *)string
{ {
BOOL inContainer = NO; BOOL inContainer = NO;
inString = NO; inPCData = NO;
if ([elementName isEqualToString: @"dict"] == YES) if ([elementName isEqualToString: @"dict"] == YES)
{ {
inContainer = YES; inContainer = YES;
@ -441,6 +441,7 @@ foundIgnorableWhitespace: (NSString *)string
@interface GSBinaryPLParser : NSObject @interface GSBinaryPLParser : NSObject
{ {
NSPropertyListMutabilityOptions mutability; NSPropertyListMutabilityOptions mutability;
unsigned _length;
const unsigned char *_bytes; const unsigned char *_bytes;
NSData *data; NSData *data;
unsigned offset_size; // Number of bytes per table entry unsigned offset_size; // Number of bytes per table entry
@ -2810,10 +2811,8 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
- (id) initWithData: (NSData*)plData - (id) initWithData: (NSData*)plData
mutability: (NSPropertyListMutabilityOptions)m mutability: (NSPropertyListMutabilityOptions)m
{ {
unsigned length; _length = [plData length];
if (_length < 32)
length = [plData length];
if (length < 32)
{ {
DESTROY(self); DESTROY(self);
} }
@ -2821,7 +2820,7 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
{ {
unsigned char postfix[32]; unsigned char postfix[32];
[plData getBytes: postfix range: NSMakeRange(length - 32, 32)]; [plData getBytes: postfix range: NSMakeRange(_length - 32, 32)];
offset_size = postfix[6]; offset_size = postfix[6];
index_size = postfix[7]; index_size = postfix[7];
// FIXME: Looks like the following are actually 8 byte values. // FIXME: Looks like the following are actually 8 byte values.
@ -2849,11 +2848,17 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
[NSException raise: NSGenericException [NSException raise: NSGenericException
format: @"Unknown table size %d", saved]; format: @"Unknown table size %d", saved];
} }
else if (table_start + object_count * offset_size > _length)
{
DESTROY(self); // Bad format
[NSException raise: NSGenericException
format: @"Table size larger than supplied data"];
}
else if (root_index >= object_count) else if (root_index >= object_count)
{ {
DESTROY(self); // Bad format DESTROY(self); // Bad format
} }
else if (table_start > length - 32) else if (table_start > _length - 32)
{ {
DESTROY(self); // Bad format DESTROY(self); // Bad format
} }
@ -2874,125 +2879,93 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
{ {
[NSException raise: NSRangeException [NSException raise: NSRangeException
format: @"Object table index out of bounds %d.", index]; format: @"Object table index out of bounds %d.", index];
} return 0; /* Not reached */
if (offset_size == 1)
{
unsigned char offset;
[data getBytes: &offset range: NSMakeRange(table_start + index, 1)];
return offset;
}
else if (offset_size == 2)
{
unsigned short offset;
[data getBytes: &offset range: NSMakeRange(table_start + 2*index, 2)];
return NSSwapBigShortToHost(offset);
} }
else else
{ {
unsigned char buffer[offset_size]; unsigned long offset;
int i; unsigned count;
unsigned long num = 0; unsigned pos;
NSRange r;
r = NSMakeRange(table_start + offset_size*index, offset_size); /* An offset is stored in big-endian byte order, so we can simply
[data getBytes: &buffer range: r]; * read it byte by byte.
for (i = 0; i < offset_size; i++) */
pos = table_start + index * offset_size;
offset = _bytes[pos++];
for (count = 1; count < offset_size; count++)
{ {
num = (num << 8) + buffer[i]; offset = (offset << 8) + _bytes[pos++];
} }
return num; return offset;
} }
return 0;
} }
- (unsigned) readObjectIndexAt: (unsigned*)counter - (unsigned) readObjectIndexAt: (unsigned*)counter
{ {
if (index_size == 1) unsigned index;
{ unsigned count;
unsigned char oid; unsigned pos;
[data getBytes: &oid range: NSMakeRange(*counter,1)]; NSAssert(0 != counter, NSInvalidArgumentException);
*counter += 1; pos = *counter;
return oid; NSAssert(pos + index_size < _length, NSInvalidArgumentException);
} index = _bytes[pos++];
else if (index_size == 2) for (count = 1; count < index_size; count++)
{ {
unsigned short oid; index = (index << 8) + _bytes[pos++];
[data getBytes: &oid range: NSMakeRange(*counter, 2)];
*counter += 2;
return NSSwapBigShortToHost(oid);
} }
else *counter = pos;
{ return index;
unsigned char buffer[index_size];
int i;
unsigned num = 0;
[data getBytes: &buffer range: NSMakeRange(*counter, index_size)];
*counter += index_size;
for (i = 0; i < index_size; i++)
{
num = (num << 8) + buffer[i];
}
return num;
}
return 0;
} }
- (unsigned long) readCountAt: (unsigned*) counter - (unsigned long) readCountAt: (unsigned*) counter
{ {
unsigned long count;
unsigned pos;
unsigned char c; unsigned char c;
[data getBytes: &c range: NSMakeRange(*counter,1)]; NSAssert(0 != counter, NSInvalidArgumentException);
*counter += 1; pos = *counter;
NSAssert(pos <= _length, NSInvalidArgumentException);
c = _bytes[pos++];
if (c == 0x10) if (c == 0x10)
{ {
unsigned char count; NSAssert(pos + 1 < _length, NSInvalidArgumentException);
count = _bytes[pos++];
[data getBytes: &count range: NSMakeRange(*counter,1)]; *counter = pos;
*counter += 1;
return count; return count;
} }
else if (c == 0x11) else if (c == 0x11)
{ {
unsigned short count; NSAssert(pos + 2 < _length, NSInvalidArgumentException);
count = _bytes[pos++];
[data getBytes: &count range: NSMakeRange(*counter,2)]; count = (count << 8) + _bytes[pos++];
*counter += 2; *counter = pos;
return NSSwapBigShortToHost(count); return count;
} }
else if ((c > 0x11) && (c <= 0x13)) else if ((c > 0x11) && (c <= 0x13))
{ {
unsigned len = c - 0x0f; unsigned len = c - 0x10;
unsigned char buffer[len];
int i;
unsigned long num = 0;
[data getBytes: &buffer range: NSMakeRange(*counter, len)]; NSAssert(pos + 1 < _length, NSInvalidArgumentException);
*counter += len; count = _bytes[pos++];
for (i = 0; i < len; i++) NSAssert(pos + count < _length, NSInvalidArgumentException);
while (len-- > 0)
{ {
num = (num << 8) + buffer[i]; count = (count << 8) + _bytes[pos++];
} }
return num; *counter = pos;
return count;
} }
else else
{ {
//FIXME //FIXME
[NSException raise: NSGenericException [NSException raise: NSGenericException
format: @"Unknown count type %d", c]; format: @"Unknown count type %d", c];
}
return 0; return 0;
} }
}
- (id) rootObject - (id) rootObject
{ {
@ -3071,6 +3044,7 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
// short data // short data
unsigned len = next - 0x40; unsigned len = next - 0x40;
NSAssert(counter + len <= _length, NSInvalidArgumentException);
if (mutability == NSPropertyListMutableContainersAndLeaves) if (mutability == NSPropertyListMutableContainersAndLeaves)
{ {
result = [NSMutableData dataWithBytes: _bytes + counter result = [NSMutableData dataWithBytes: _bytes + counter
@ -3078,7 +3052,8 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
} }
else else
{ {
result = [data subdataWithRange: NSMakeRange(counter, len)]; result = [NSData dataWithBytes: _bytes + counter
length: len];
} }
} }
else if (next == 0x4F) else if (next == 0x4F)
@ -3087,6 +3062,7 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
unsigned long len; unsigned long len;
len = [self readCountAt: &counter]; len = [self readCountAt: &counter];
NSAssert(counter + len <= _length, NSInvalidArgumentException);
if (mutability == NSPropertyListMutableContainersAndLeaves) if (mutability == NSPropertyListMutableContainersAndLeaves)
{ {
result = [NSMutableData dataWithBytes: _bytes + counter result = [NSMutableData dataWithBytes: _bytes + counter
@ -3094,95 +3070,85 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
} }
else else
{ {
result = [data subdataWithRange: NSMakeRange(counter, len)]; result = [NSData dataWithBytes: _bytes + counter
length: len];
} }
} }
else if ((next >= 0x50) && (next < 0x5F)) else if ((next >= 0x50) && (next < 0x5F))
{ {
// Short string NSString *s; // Short utf8 string
unsigned len = next - 0x50; unsigned len;
char buffer[len+1];
[data getBytes: buffer range: NSMakeRange(counter, len)];
buffer[len] = '\0';
if (mutability == NSPropertyListMutableContainersAndLeaves) if (mutability == NSPropertyListMutableContainersAndLeaves)
{ {
result = [NSMutableString stringWithUTF8String: buffer]; s = [NSMutableString alloc];
} }
else else
{ {
result = [NSString stringWithUTF8String: buffer]; s = [NSString alloc];
} }
len = next - 0x50;
s = [s initWithBytes: _bytes + counter
length: len
encoding: NSUTF8StringEncoding];
result = [s autorelease];
} }
else if (next == 0x5F) else if (next == 0x5F)
{ {
// long string NSString *s; // Long utf8 string
unsigned long len; unsigned len;
char *buffer;
len = [self readCountAt: &counter];
buffer = NSAllocateCollectable(len + 1, 0);
[data getBytes: buffer range: NSMakeRange(counter, len)];
buffer[len] = '\0';
if (mutability == NSPropertyListMutableContainersAndLeaves) if (mutability == NSPropertyListMutableContainersAndLeaves)
{ {
result = [NSMutableString stringWithUTF8String: buffer]; s = [NSMutableString alloc];
} }
else else
{ {
result = [NSString stringWithUTF8String: buffer]; s = [NSString alloc];
} }
NSZoneFree(NSDefaultMallocZone(), buffer); len = [self readCountAt: &counter];
s = [s initWithBytes: _bytes + counter
length: len
encoding: NSUTF8StringEncoding];
result = [s autorelease];
} }
else if ((next >= 0x60) && (next < 0x6F)) else if ((next >= 0x60) && (next < 0x6F))
{ {
// Short unicode string NSString *s; // Short unicode string
unsigned len = next - 0x60; unsigned len;
unsigned i;
unichar buffer[len];
[data getBytes: buffer
range: NSMakeRange(counter, sizeof(unichar)*len)];
for (i = 0; i < len; i++)
{
buffer[i] = NSSwapBigShortToHost(buffer[i]);
}
if (mutability == NSPropertyListMutableContainersAndLeaves) if (mutability == NSPropertyListMutableContainersAndLeaves)
{ {
result = [NSMutableString stringWithCharacters: buffer length: len]; s = [NSMutableString alloc];
} }
else else
{ {
result = [NSString stringWithCharacters: buffer length: len]; s = [NSString alloc];
} }
len = next - 0x60;
s = [s initWithBytes: _bytes + counter
length: len * sizeof(unichar)
encoding: NSUTF16BigEndianStringEncoding];
result = [s autorelease];
} }
else if (next == 0x6F) else if (next == 0x6F)
{ {
// long unicode string NSString *s; // Short unicode string
unsigned long len; unsigned long len;
unsigned i;
unichar *buffer;
len = [self readCountAt: &counter];
buffer = NSAllocateCollectable(sizeof(unichar) * len, 0);
[data getBytes: buffer range: NSMakeRange(counter, sizeof(unichar)*len)];
for (i = 0; i < len; i++)
{
buffer[i] = NSSwapBigShortToHost(buffer[i]);
}
if (mutability == NSPropertyListMutableContainersAndLeaves) if (mutability == NSPropertyListMutableContainersAndLeaves)
{ {
result = [NSMutableString stringWithCharacters: buffer length: len]; s = [NSMutableString alloc];
} }
else else
{ {
result = [NSString stringWithCharacters: buffer length: len]; s = [NSString alloc];
} }
NSZoneFree(NSDefaultMallocZone(), buffer); len = [self readCountAt: &counter];
s = [s initWithBytes: _bytes + counter
length: len * sizeof(unichar)
encoding: NSUTF16BigEndianStringEncoding];
result = [s autorelease];
} }
else if (next == 0x80) else if (next == 0x80)
{ {
@ -3342,7 +3308,7 @@ GSPropertyListMake(id obj, NSDictionary *loc, BOOL xml,
@end @end
/* Test two items for equality ... boith are objects. /* Test two items for equality ... both are objects.
* If either is an NSNumber, we insist that they are the same class * If either is an NSNumber, we insist that they are the same class
* so that numbers with the same numeric value but different classes * so that numbers with the same numeric value but different classes
* are not treated as the same number (that confuses OSXs decoding). * are not treated as the same number (that confuses OSXs decoding).
@ -3720,71 +3686,59 @@ isEqualFunc(const void *item1, const void *item2,
- (void) storeString: (NSString*) string - (void) storeString: (NSString*) string
{ {
unsigned int len; unsigned int len;
BOOL ascii = YES; NSData *ascii;
unsigned char code; unsigned char code;
unsigned int i;
unichar uchar;
len = [string length]; len = [string length];
for (i = 0; i < len; i++) ascii = [string dataUsingEncoding: NSASCIIStringEncoding
{ allowLossyConversion: NO];
uchar = [string characterAtIndex: i];
if (uchar > 127)
{
ascii = NO;
break;
}
}
if (ascii) if (ascii)
{ {
if (len < 0x0F) if (len < 0x0F)
{ {
code = 0x50 + len; code = 0x50 + len;
[dest appendBytes: &code length: 1]; [dest appendBytes: &code length: 1];
[dest appendBytes: [string cString] length: len]; [dest appendData: ascii];
} }
else else
{ {
code = 0x5F; code = 0x5F;
[dest appendBytes: &code length: 1]; [dest appendBytes: &code length: 1];
[self storeCount: len]; [self storeCount: len];
[dest appendBytes: [string cString] length: len]; [dest appendData: ascii];
} }
} }
else else
{ {
NSUInteger offset;
uint8_t *buffer;
if (len < 0x0F) if (len < 0x0F)
{ {
unichar buffer[len + 1];
int i;
code = 0x60 + len; code = 0x60 + len;
[dest appendBytes: &code length: 1]; [dest appendBytes: &code length: 1];
[string getCharacters: buffer];
for (i = 0; i < len; i++)
{
buffer[i] = NSSwapHostShortToBig(buffer[i]);
}
[dest appendBytes: buffer length: len * sizeof(unichar)];
} }
else else
{ {
unichar *buffer;
code = 0x6F; code = 0x6F;
[dest appendBytes: &code length: 1]; [dest appendBytes: &code length: 1];
buffer = NSZoneMalloc(0, sizeof(unichar)*(len + 1));
[self storeCount: len]; [self storeCount: len];
[string getCharacters: buffer]; }
offset = [dest length];
[dest setLength: offset + sizeof(unichar)*len];
buffer = [dest mutableBytes] + offset;
[string getCharacters: (unichar*)buffer];
#if GS_WORDS_BIGENDIAN
for (i = 0; i < len; i++) for (i = 0; i < len; i++)
{ {
buffer[i] = NSSwapHostShortToBig(buffer[i]); uint8_t o = *buffer++;
}
[dest appendBytes: buffer length: sizeof(unichar)*len]; buffer[-1] = *buffer;
NSZoneFree(0, buffer); *buffer++ = o;
} }
#endif
} }
} }