Various bugfixes, portability fixes, and optimisations.

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@22576 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
Richard Frith-MacDonald 2006-02-27 09:35:19 +00:00
parent 5d671ce847
commit 854cd456b0
15 changed files with 879 additions and 369 deletions

View file

@ -1,3 +1,33 @@
2006-02-27 Richard Frith-Macdonald <rfm@gnu.org>
* Headers/Foundation/NSString.h: Correct return type for
([getCString:maxLength:encoding])
* Source/NSString.m: ([getCString:maxLength:encoding]) make
implementation match MacOS-X implementation rather than their docs.
Change API for setting path handling mode to be a function we can
call before any string/path operations. Maybe final API to be made
public?
Path handling tweaks based on discussion at FOSDEM
* Source/GSString.m: ([getCString:maxLength:encoding]) implemented.
* Source/unix/NSStream.m: Portabiulity fixups ... use EPROTO only
if defined and use dummy implementations of inet6 cclasses if AF_INET6
is not defined.
* Source/NSKeyValueCoding.m: Some optimisation suggested by Helge ...
rewrite key path methods to loop rather than recurse.
* Source/GSFFIInvocation.m: Avoid compiler warning
* Source/NSURL.m: use new getCString... method
* Source/NSSerializer.m: ditto
* Documentation/Base.gsdoc: Remove env variable to set path handling.
* Headers/Additions/GNUstepBase/GSObjCRuntime.h: Slight change to
functions for KVC to allow faster implementation.
* Source/Additions/GSObjCRuntime.m: ditto
2006-02-24 Richard Frith-Macdonald <rfm@gnu.org>
* NSTimeZone.m: Fix bug in GMT+/-NNNN timezone initialisation so that
negative offsets work. Implement GMT and synonyms as internal
absolute timezones. Implement GMT-14 to GMT+14 as absolute timezones.
2006-02-23 Richard Frith-Macdonald <rfm@gnu.org>
* Source/NSUserDefaults.m: Restructure for lazy creation of defaults

View file

@ -276,21 +276,6 @@ notice and this notice are preserved.
GNUstep defaults to NSISOLatin1StringEncoding.
</p>
</desc>
<term>GNUSTEP_PATH_HANDLING</term>
<desc>
<p>
May be set to <code>unix</code> to enforce unix style path
handling, or <code>windows</code> to enforce mswindows style
path handling, or any other value (including unset) for the
default behavior where both styles of paths should be
managed in the best way possible.
</p>
<p>
The option to enforce either pure unix or pure windows style
path handling (and hence this environment variable) may be
removed in a later release.
</p>
</desc>
<term>GNUSTEP_HOST_CPU</term>
<desc>
<p>
@ -344,26 +329,28 @@ notice and this notice are preserved.
</desc>
<term>GNUSTEP_CONFIG_FILE</term>
<desc>
This has no effect unless the base library has been
configured/built with the
<code>--enable-environment-config-file</code> option.<br />
If it is operational, the environment variable overrides the
normal path to the gnustep config file used to determine the
locations of paths for the gnustep system (see later).<br />
This is provided to support the odd situation where you may
want to simultaneously run applications using different sets
of resources but linked to a lingle copy of the base library.
<p>
This has no effect unless the base library has been
configured/built with the
<code>--enable-environment-config-file</code> option.<br />
If it is operational, the environment variable overrides the
normal path to the gnustep config file used to determine the
locations of paths for the gnustep system (see later).<br />
This is provided to support the odd situation where you may
want to simultaneously run applications using different sets
of resources but linked to a lingle copy of the base library.
</p>
</desc>
<term>HOMEDRIVE</term>
<desc>
<p>
Used on windoze to locate the home directory.
Used on ms-windows to locate the home directory.
</p>
</desc>
<term>HOMEPATH</term>
<desc>
<p>
Used on windoze to locate the home directory.
Used on ms-windows to locate the home directory.
</p>
</desc>
<term>LANGUAGES</term>

View file

@ -135,12 +135,12 @@ GSObjCAddClasses(NSArray *classes);
* scalar types of data.
*/
GS_EXPORT id
GSObjCGetValue(NSObject *self, NSString *key, SEL sel,
const char *type, unsigned size, int offset);
GSObjCGetVal(NSObject *self, const char *key, SEL sel,
const char *type, unsigned size, int offset);
GS_EXPORT void
GSObjCSetValue(NSObject *self, NSString *key, id val, SEL sel,
const char *type, unsigned size, int offset);
GSObjCSetVal(NSObject *self, const char *key, id val, SEL sel,
const char *type, unsigned size, int offset);
#include <GNUstepBase/objc-gnu2next.h>

View file

@ -79,7 +79,7 @@ GNUstepConfig(NSDictionary *newConfig);
* fromm it.
*/
GS_EXPORT NSString*
GSDefaultsRootForUser(NSString *username);
GSDefaultsRootForUser(NSString *userName);
/**
* The config dictionary passed to this function should be a

View file

@ -18,7 +18,8 @@
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111 USA.
Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
Boston, MA 02111 USA.
*/
#ifndef __NSString_h_GNUSTEP_BASE_INCLUDE
@ -176,7 +177,7 @@ enum {
+ (id) string;
+ (id) stringWithCharacters: (const unichar*)chars
length: (unsigned int)length;
#ifndef STRICT_OPENSTEP
#if OS_API_VERSION(100400,GS_API_LATEST) && GS_API_VERSION(010200,GS_API_LATEST)
+ (id) stringWithCString: (const char*)byteString
encoding: (NSStringEncoding)encoding;
#endif
@ -188,7 +189,7 @@ enum {
// Initializing Newly Allocated Strings
- (id) init;
#ifndef STRICT_OPENSTEP
#if OS_API_VERSION(100400,GS_API_LATEST) && GS_API_VERSION(010200,GS_API_LATEST)
- (id) initWithBytes: (const void*)bytes
length: (unsigned int)length
encoding: (NSStringEncoding)encoding;
@ -285,7 +286,7 @@ enum {
#if OS_API_VERSION(100400,GS_API_LATEST) && GS_API_VERSION(010200,GS_API_LATEST)
- (const char*) cStringUsingEncoding: (NSStringEncoding)encoding;
- (void) getCString: (char*)buffer
- (BOOL) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
encoding: (NSStringEncoding)encoding;
- (id) initWithCString: (const char*)byteString

View file

@ -1476,12 +1476,12 @@ GSObjCAddClassBehavior(Class receiver, Class behavior)
#endif
/** Deprecated ... use GSObjCGetValue() */
/** Deprecated ... use GSObjCGetVal() */
id
GSGetValue(NSObject *self, NSString *key, SEL sel,
const char *type, unsigned size, int offset)
{
return GSObjCGetValue(self, key, sel, type, size, offset);
return GSObjCGetVal(self, [key UTF8String], sel, type, size, offset);
}
/**
* This is used internally by the key-value coding methods, to get a
@ -1494,7 +1494,7 @@ GSGetValue(NSObject *self, NSString *key, SEL sel,
* to get a value.
*/
id
GSObjCGetValue(NSObject *self, NSString *key, SEL sel,
GSObjCGetVal(NSObject *self, const char *key, SEL sel,
const char *type, unsigned size, int offset)
{
if (sel != 0)
@ -1510,7 +1510,7 @@ GSObjCGetValue(NSObject *self, NSString *key, SEL sel,
}
if (type == NULL)
{
return [self valueForUndefinedKey: key];
return [self valueForUndefinedKey: [NSString stringWithUTF8String: key]];
}
else
{
@ -1792,13 +1792,22 @@ GSObjCGetValue(NSObject *self, NSString *key, SEL sel,
return val;
}
}
/**
* Calls GSObjCGetVal()
*/
id
GSObjCGetValue(NSObject *self, NSString *key, SEL sel,
const char *type, unsigned size, int offset)
{
return GSObjCGetVal(self, [key UTF8String], sel, type, size, offset);
}
/** Deprecated ... use GSObjCSetValue() */
/** Deprecated ... use GSObjCSetVal() */
void
GSSetValue(NSObject *self, NSString *key, id val, SEL sel,
const char *type, unsigned size, int offset)
{
GSObjCSetValue(self, key, val, sel, type, size, offset);
GSObjCSetVal(self, [key UTF8String], val, sel, type, size, offset);
}
/**
* This is used internally by the key-value coding methods, to set a
@ -1811,8 +1820,8 @@ GSSetValue(NSObject *self, NSString *key, id val, SEL sel,
* to set a value.
*/
void
GSObjCSetValue(NSObject *self, NSString *key, id val, SEL sel,
const char *type, unsigned size, int offset)
GSObjCSetVal(NSObject *self, const char *key, id val, SEL sel,
const char *type, unsigned size, int offset)
{
static NSNull *null = nil;
@ -1833,11 +1842,12 @@ GSObjCSetValue(NSObject *self, NSString *key, id val, SEL sel,
}
if (type == NULL)
{
[self setValue: val forUndefinedKey: key];
[self setValue: val
forUndefinedKey: [NSString stringWithUTF8String: key]];
}
else if ((val == nil || val == null) && *type != _C_ID && *type != _C_CLASS)
{
[self setNilValueForKey: key];
[self setNilValueForKey: [NSString stringWithUTF8String: key]];
}
else
{
@ -2121,6 +2131,15 @@ GSObjCSetValue(NSObject *self, NSString *key, id val, SEL sel,
}
}
}
/**
* Calls GSObjCSetVal()
*/
void
GSObjCSetValue(NSObject *self, NSString *key, id val, SEL sel,
const char *type, unsigned size, int offset)
{
GSObjCSetVal(self, [key UTF8String], val, sel, type, size, offset);
}
/** Returns an autoreleased array of subclasses of Class cls, including

View file

@ -235,7 +235,6 @@ static IMP gs_objc_msg_forward (SEL sel)
frame: (cifframe_t *)frame
signature: (NSMethodSignature*)aSignature
{
int i;
_sig = RETAIN(aSignature);
_numArgs = [aSignature numberOfArguments];
_info = [aSignature methodInfo];
@ -243,6 +242,8 @@ static IMP gs_objc_msg_forward (SEL sel)
((cifframe_t *)_cframe)->cif = *cif;
#if MFRAME_STRUCT_BYREF
{
int i;
/* Fix up some of the values. Do this on all processors that pass
structs by reference. Is there an automatic way to determine this? */
for (i = 0; i < ((cifframe_t *)_cframe)->nargs; i++)
@ -260,6 +261,7 @@ static IMP gs_objc_msg_forward (SEL sel)
((cifframe_t *)_cframe)->arg_types[i]->size);
}
}
}
#else
((cifframe_t *)_cframe)->values = vals;
#endif

View file

@ -1021,9 +1021,7 @@ cString_c(GSStr self, NSStringEncoding enc)
unsigned l = 0;
/*
* The external C string encoding is not compatible with the internal
* 8-bit character strings ... we must convert from internal format to
* unicode and then to the external C string encoding.
* The external C string encoding is unicode ... convert to it.
*/
if (GSToUnicode((unichar**)&r, &l, self->_contents.c, self->_count,
intEnc, NSDefaultMallocZone(),
@ -1458,6 +1456,222 @@ getCString_u(GSStr self, char *buffer, unsigned int maxLength,
}
}
static inline BOOL
getCStringE_c(GSStr self, char *buffer, unsigned int maxLength,
NSStringEncoding enc)
{
if (enc == NSUnicodeStringEncoding)
{
if (maxLength >= sizeof(unichar))
{
unsigned bytes = maxLength - sizeof(unichar);
unichar *u = (unichar*)buffer;
if (GSToUnicode(&u, &bytes, self->_contents.c, self->_count, intEnc,
NSDefaultMallocZone(), GSUniTerminate) == NO)
{
[NSException raise: NSCharacterConversionException
format: @"Can't convert to Unicode string."];
}
if (u == (unichar*)buffer)
{
return YES;
}
NSZoneFree(NSDefaultMallocZone(), u);
}
return NO;
}
else
{
if (maxLength > sizeof(char))
{
unsigned bytes = maxLength - sizeof(char);
if (enc == intEnc)
{
if (bytes > self->_count)
{
bytes = self->_count;
}
memcpy(buffer, self->_contents.c, bytes);
buffer[bytes] = '\0';
if (bytes < self->_count)
{
return NO;
}
return YES;
}
else if (enc == NSASCIIStringEncoding && GSIsByteEncoding(intEnc))
{
unsigned i;
if (bytes > self->_count)
{
bytes = self->_count;
}
for (i = 0; i < bytes; i++)
{
unsigned char c = self->_contents.c[i];
if (c > 127)
{
[NSException raise: NSCharacterConversionException
format: @"unable to convert to encoding"];
}
buffer[i] = c;
}
buffer[bytes] = '\0';
if (bytes < self->_count)
{
return NO;
}
return YES;
}
else
{
unichar *u = 0;
unsigned char *c = (unsigned char*)buffer;
unsigned l = 0;
/*
* The specified C string encoding is not compatible with
* the internal 8-bit character strings ... we must convert
* from internal format to unicode and then to the specified
* C string encoding.
*/
if (GSToUnicode(&u, &l, self->_contents.c, self->_count, intEnc,
NSDefaultMallocZone(), 0) == NO)
{
[NSException raise: NSCharacterConversionException
format: @"Can't convert to Unicode string."];
}
if (GSFromUnicode((unsigned char**)&c, &bytes, u, l, enc,
NSDefaultMallocZone(), GSUniTerminate|GSUniStrict) == NO)
{
NSZoneFree(NSDefaultMallocZone(), u);
[NSException raise: NSCharacterConversionException
format: @"Can't convert from Unicode string."];
}
NSZoneFree(NSDefaultMallocZone(), u);
if (c == (unsigned char*)buffer)
{
return YES; // Fitted in original buffer
}
else
{
NSZoneFree(NSDefaultMallocZone(), c);
}
}
}
return NO;
}
}
static inline BOOL
getCStringE_u(GSStr self, char *buffer, unsigned int maxLength,
NSStringEncoding enc)
{
if (enc == NSUnicodeStringEncoding)
{
if (maxLength >= sizeof(unichar))
{
unsigned bytes = maxLength - sizeof(unichar);
if (bytes/sizeof(unichar) > self->_count)
{
bytes = self->_count * sizeof(unichar);
}
memcpy(buffer, self->_contents.u, bytes);
buffer[bytes] = '\0';
buffer[bytes + 1] = '\0';
if (bytes/sizeof(unichar) == self->_count)
{
return YES;
}
}
return NO;
}
else
{
if (maxLength >= 1)
{
if (enc == NSISOLatin1StringEncoding)
{
unsigned bytes = maxLength - sizeof(char);
unsigned i;
if (bytes > self->_count)
{
bytes = self->_count;
}
for (i = 0; i < bytes; i++)
{
unichar u = self->_contents.u[i];
if (u & 0xff00)
{
[NSException raise: NSCharacterConversionException
format: @"unable to convert to encoding"];
}
buffer[i] = (char)u;
}
buffer[i++] = '\0';
if (bytes == self->_count)
{
return YES;
}
}
else if (enc == NSASCIIStringEncoding)
{
unsigned bytes = maxLength - sizeof(char);
unsigned i;
if (bytes > self->_count)
{
bytes = self->_count;
}
for (i = 0; i < bytes; i++)
{
unichar u = self->_contents.u[i];
if (u & 0xff80)
{
[NSException raise: NSCharacterConversionException
format: @"unable to convert to encoding"];
}
buffer[i] = (char)u;
}
buffer[i++] = '\0';
if (bytes == self->_count)
{
return YES;
}
}
else
{
unsigned char *c = (unsigned char*)buffer;
if (GSFromUnicode((unsigned char**)&c, &maxLength,
self->_contents.u, self->_count, enc,
NSDefaultMallocZone(), GSUniTerminate|GSUniStrict) == NO)
{
[NSException raise: NSCharacterConversionException
format: @"Can't convert to/from Unicode string."];
}
if (c == (unsigned char*)buffer)
{
return YES;
}
else
{
NSZoneFree(NSDefaultMallocZone(), c);
}
}
}
return NO;
}
}
static inline int
intValue_c(GSStr self)
{
@ -2302,6 +2516,13 @@ transmute(GSStr self, NSString *aString)
getCString_c((GSStr)self, buffer, maxLength, (NSRange){0, _count}, 0);
}
- (BOOL) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
encoding: (NSStringEncoding)encoding
{
return getCStringE_c((GSStr)self, buffer, maxLength, encoding);
}
- (void) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
range: (NSRange)aRange
@ -2633,6 +2854,12 @@ agree, create a new GSCInlineString otherwise.
getCString_u((GSStr)self, buffer, maxLength, (NSRange){0, _count}, 0);
}
- (BOOL) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
encoding: (NSStringEncoding)encoding
{
return getCStringE_u((GSStr)self, buffer, maxLength, encoding);
}
- (void) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
range: (NSRange)aRange
@ -3125,6 +3352,16 @@ agree, create a new GSUnicodeInlineString otherwise.
getCString_c((GSStr)self, buffer, maxLength, (NSRange){0, _count}, 0);
}
- (BOOL) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
encoding: (NSStringEncoding)encoding
{
if (_flags.wide == 1)
return getCStringE_u((GSStr)self, buffer, maxLength, encoding);
else
return getCStringE_c((GSStr)self, buffer, maxLength, encoding);
}
- (void) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
range: (NSRange)aRange
@ -3748,11 +3985,11 @@ agree, create a new GSUnicodeInlineString otherwise.
[_parent getCString: buffer maxLength: maxLength];
}
- (void) getCString: (char*)buffer
- (BOOL) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
encoding: (NSStringEncoding)encoding
{
[_parent getCString: buffer maxLength: maxLength encoding: encoding];
return [_parent getCString: buffer maxLength: maxLength encoding: encoding];
}
- (void) getCString: (char*)buffer

View file

@ -17,7 +17,8 @@
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111 USA.
Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
Boston, MA 02111 USA.
<title>NSKeyValueCoding informal protocol reference</title>
$Date$ $Revision$
@ -39,6 +40,145 @@
NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
static void
SetValueForKey(NSObject *self, id anObject, const char *key, unsigned size)
{
SEL sel = 0;
const char *type = 0;
int off;
if (size > 0)
{
const char *name;
char buf[size+6];
char lo;
char hi;
strcpy(buf, "_set");
strcpy(&buf[4], key);
lo = buf[4];
hi = islower(lo) ? toupper(lo) : lo;
buf[4] = hi;
buf[size+4] = ':';
buf[size+5] = '\0';
name = &buf[1]; // setKey:
type = NULL;
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
name = buf; // _setKey:
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
sel = 0;
if ([[self class] accessInstanceVariablesDirectly] == YES)
{
buf[size+4] = '\0';
buf[3] = '_';
buf[4] = lo;
name = &buf[3]; // _key
if (GSObjCFindVariable(self, name, &type, &size, &off) == NO)
{
buf[4] = hi;
buf[3] = 's';
buf[2] = 'i';
buf[1] = '_';
name = &buf[1]; // _isKey
if (GSObjCFindVariable(self,
name, &type, &size, &off) == NO)
{
buf[4] = lo;
name = &buf[4]; // key
if (GSObjCFindVariable(self,
name, &type, &size, &off) == NO)
{
buf[4] = hi;
buf[3] = 's';
buf[2] = 'i';
name = &buf[2]; // isKey
GSObjCFindVariable(self,
name, &type, &size, &off);
}
}
}
}
}
else
{
GSOnceFLog(@"Key-value access using _setKey: isdeprecated:");
}
}
}
GSObjCSetVal(self, key, anObject, sel, type, size, off);
}
static id ValueForKey(NSObject *self, const char *key, unsigned size)
{
SEL sel = 0;
int off;
const char *type = NULL;
if (size > 0)
{
const char *name;
char buf[size+5];
char lo;
char hi;
strcpy(buf, "_get");
strcpy(&buf[4], key);
lo = buf[4];
hi = islower(lo) ? toupper(lo) : lo;
buf[4] = hi;
name = &buf[1]; // getKey
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
buf[4] = lo;
name = &buf[4]; // key
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
sel = 0;
}
}
if (sel == 0 && [[self class] accessInstanceVariablesDirectly] == YES)
{
buf[4] = hi;
name = buf; // _getKey
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
buf[4] = lo;
buf[3] = '_';
name = &buf[3]; // _key
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
sel = 0;
}
}
if (sel == 0)
{
buf[4] = lo;
buf[3] = '_';
name = &buf[4]; // key
if (GSObjCFindVariable(self, name, &type, &size, &off) == NO)
{
name = &buf[3]; // _key
GSObjCFindVariable(self, name, &type, &size, &off);
}
}
}
}
return GSObjCGetVal(self, key, sel, type, size, off);
}
@implementation NSObject(KeyValueCoding)
+ (BOOL) accessInstanceVariablesDirectly
@ -143,93 +283,42 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
- (void) setValue: (id)anObject forKey: (NSString*)aKey
{
SEL sel = 0;
const char *type = 0;
int off;
unsigned size = [aKey length];
char key[size+1];
if (size > 0)
{
const char *name;
char buf[size+6];
char lo;
char hi;
strcpy(buf, "_set");
[aKey getCString: &buf[4]];
lo = buf[4];
hi = islower(lo) ? toupper(lo) : lo;
buf[4] = hi;
buf[size+4] = ':';
buf[size+5] = '\0';
name = &buf[1]; // setKey:
type = NULL;
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
name = buf; // _setKey:
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
sel = 0;
if ([[self class] accessInstanceVariablesDirectly] == YES)
{
buf[size+4] = '\0';
buf[3] = '_';
buf[4] = lo;
name = &buf[3]; // _key
if (GSObjCFindVariable(self, name, &type, &size, &off) == NO)
{
buf[4] = hi;
buf[3] = 's';
buf[2] = 'i';
buf[1] = '_';
name = &buf[1]; // _isKey
if (GSObjCFindVariable(self,
name, &type, &size, &off) == NO)
{
buf[4] = lo;
name = &buf[4]; // key
if (GSObjCFindVariable(self,
name, &type, &size, &off) == NO)
{
buf[4] = hi;
buf[3] = 's';
buf[2] = 'i';
name = &buf[2]; // isKey
GSObjCFindVariable(self,
name, &type, &size, &off);
}
}
}
}
}
else
{
GSOnceMLog(@"Key-value access using _setKey: isdeprecated:");
}
}
}
GSObjCSetValue(self, aKey, anObject, sel, type, size, off);
[aKey getCString: key
maxLength: size+1
encoding: NSASCIIStringEncoding];
SetValueForKey(self, anObject, key, size);
}
- (void) setValue: (id)anObject forKeyPath: (NSString*)aKey
{
NSRange r = [aKey rangeOfString: @"."];
unsigned size = [aKey length];
char buf[size+1];
unsigned start = 0;
unsigned end = 0;
id o = self;
if (r.length == 0)
[aKey getCString: buf
maxLength: size+1
encoding: NSASCIIStringEncoding];
while (o != nil)
{
[self setValue: anObject forKey: aKey];
}
else
{
NSString *key = [aKey substringToIndex: r.location];
NSString *path = [aKey substringFromIndex: NSMaxRange(r)];
[[self valueForKey: key] setValue: anObject forKeyPath: path];
end = start;
while (end < size && buf[end] != '.')
{
end++;
}
if (end >= size)
{
break;
}
o = ValueForKey(o, buf + start, end - start);
start = ++end;
}
SetValueForKey(o, anObject, buf + start, end - start);
}
@ -284,19 +373,23 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
return [self valueForKey: aKey];
}
size = [aKey cStringLength];
size = [aKey length];
if (size > 0)
{
SEL sel = 0;
const char *type = NULL;
int off;
const char *name;
char key[size+1];
char buf[size+5];
char lo;
char hi;
strcpy(buf, "_get");
[aKey getCString: &buf[4]];
[aKey getCString: key
maxLength: size+1
encoding: NSASCIIStringEncoding];
strcpy(&buf[4], key);
lo = buf[4];
hi = islower(lo) ? toupper(lo) : lo;
buf[4] = hi;
@ -345,7 +438,7 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
}
if (sel != 0 || type != NULL)
{
return GSObjCGetValue(self, aKey, sel, type, size, off);
return GSObjCGetVal(self, key, sel, type, size, off);
}
}
[self handleTakeValue: nil forUnboundKey: aKey];
@ -370,12 +463,16 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
const char *type;
int off;
const char *name;
char key[size+1];
char buf[size+6];
char lo;
char hi;
strcpy(buf, "_set");
[aKey getCString: &buf[4]];
[aKey getCString: key
maxLength: size+1
encoding: NSASCIIStringEncoding];
strcpy(&buf[4], key);
lo = buf[4];
hi = islower(lo) ? toupper(lo) : lo;
buf[4] = hi;
@ -415,7 +512,7 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
}
if (sel != 0 || type != NULL)
{
GSObjCSetValue(self, aKey, anObject, sel, type, size, off);
GSObjCSetVal(self, key, anObject, sel, type, size, off);
return;
}
}
@ -448,8 +545,12 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
const char *type = 0;
int off;
unsigned size = [aKey length];
char key[size+1];
GSOnceMLog(@"This method is deprecated, use -setValue:forKey:");
[aKey getCString: key
maxLength: size+1
encoding: NSASCIIStringEncoding];
if (size > 0)
{
const char *name;
@ -458,7 +559,7 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
char hi;
strcpy(buf, "_set");
[aKey getCString: &buf[4]];
strcpy(&buf[4], key);
lo = buf[4];
hi = islower(lo) ? toupper(lo) : lo;
buf[4] = hi;
@ -490,7 +591,7 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
}
}
}
GSObjCSetValue(self, aKey, anObject, sel, type, size, off);
GSObjCSetVal(self, key, anObject, sel, type, size, off);
}
@ -546,22 +647,33 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
forKey: (NSString*)aKey
error: (NSError**)anError
{
NSString *name;
const char *str = [aKey cString];
SEL sel;
BOOL (*imp)(id,SEL,id*,id*);
unsigned size;
if (aValue == 0 || str == 0 || *str == '\0')
if (aValue == 0 || (size = [aKey length]) == 0)
{
[NSException raise: NSInvalidArgumentException format: @"nil argument"];
}
name = [NSString stringWithFormat: @"validate%c%s:error:",
islower(*str) ? toupper(*str) : *str, str + 1];
sel = NSSelectorFromString(name);
if (sel != 0
&& (imp = (BOOL (*)(id,SEL,id*,id*))[self methodForSelector: sel]) != 0)
else
{
return (*imp)(self, sel, aValue, anError);
char name[size+16];
SEL sel;
BOOL (*imp)(id,SEL,id*,id*);
strcpy(name, "validate");
[aKey getCString: &name[8]
maxLength: size+1
encoding: NSASCIIStringEncoding];
strcpy(&name[size+8], ":error:");
if (islower(name[8]))
{
name[8] = toupper(name[8]);
}
sel = GSSelectorFromName(name);
if (sel != 0
&& (imp = (BOOL (*)(id,SEL,id*,id*))[self methodForSelector: sel]) != 0)
{
return (*imp)(self, sel, aValue, anError);
}
}
return YES;
}
@ -570,106 +682,91 @@ NSString* const NSUndefinedKeyException = @"NSUndefinedKeyException";
forKeyPath: (NSString*)aKey
error: (NSError**)anError
{
NSRange r = [aKey rangeOfString: @"."];
BOOL result;
unsigned size = [aKey length];
char buf[size+1];
unsigned start = 0;
unsigned end = 0;
id o = self;
if (r.length == 0)
[aKey getCString: buf
maxLength: size+1
encoding: NSASCIIStringEncoding];
while (o != nil)
{
result = [self validateValue: aValue forKey: aKey error: anError];
end = start;
while (end < size && buf[end] != '.')
{
end++;
}
if (end >= size)
{
break;
}
o = ValueForKey(o, buf + start, end - start);
start = ++end;
}
if (o == nil)
{
return NO;
}
else
{
NSString *key = [aKey substringToIndex: r.location];
NSString *path = [aKey substringFromIndex: NSMaxRange(r)];
char name[end-start+16];
SEL sel;
BOOL (*imp)(id,SEL,id*,id*);
result = [[self valueForKey: key]
validateValue: aValue forKeyPath: path error: anError];
size = end - start;
strcpy(name, "validate");
strcpy(&name[8], buf+start);
strcpy(&name[size+8], ":error:");
if (islower(name[8]))
{
name[8] = toupper(name[8]);
}
sel = GSSelectorFromName(name);
if (sel != 0
&& (imp = (BOOL (*)(id,SEL,id*,id*))[self methodForSelector: sel]) != 0)
{
return (*imp)(self, sel, aValue, anError);
}
return YES;
}
return result;
}
- (id) valueForKey: (NSString*)aKey
{
unsigned size;
SEL sel = 0;
int off;
const char *type = NULL;
unsigned size = [aKey length];
char key[size+1];
size = [aKey length];
if (size > 0)
{
const char *name;
char buf[size+5];
char lo;
char hi;
strcpy(buf, "_get");
[aKey getCString: &buf[4]];
lo = buf[4];
hi = islower(lo) ? toupper(lo) : lo;
buf[4] = hi;
name = &buf[1]; // getKey
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
buf[4] = lo;
name = &buf[4]; // key
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
sel = 0;
}
}
if (sel == 0 && [[self class] accessInstanceVariablesDirectly] == YES)
{
buf[4] = hi;
name = buf; // _getKey
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
buf[4] = lo;
buf[3] = '_';
name = &buf[3]; // _key
sel = GSSelectorFromName(name);
if (sel == 0 || [self respondsToSelector: sel] == NO)
{
sel = 0;
}
}
if (sel == 0)
{
buf[4] = lo;
buf[3] = '_';
name = &buf[4]; // key
if (GSObjCFindVariable(self, name, &type, &size, &off) == NO)
{
name = &buf[3]; // _key
GSObjCFindVariable(self, name, &type, &size, &off);
}
}
}
}
return GSObjCGetValue(self, aKey, sel, type, size, off);
[aKey getCString: key
maxLength: size+1
encoding: NSASCIIStringEncoding];
return ValueForKey(self, key, size);
}
- (id) valueForKeyPath: (NSString*)aKey
{
NSRange r = [aKey rangeOfString: @"."];
id o;
unsigned size = [aKey length];
char buf[size+1];
unsigned start = 0;
unsigned end = 0;
id o = nil;
if (r.length == 0)
[aKey getCString: buf
maxLength: size+1
encoding: NSASCIIStringEncoding];
while (start < size && self != nil)
{
o = [self valueForKey: aKey];
}
else
{
NSString *key = [aKey substringToIndex: r.location];
NSString *path = [aKey substringFromIndex: NSMaxRange(r)];
o = [[self valueForKey: key] valueForKeyPath: path];
end = start;
while (end < size && buf[end] != '.')
{
end++;
}
o = ValueForKey(self, buf + start, end - start);
start = ++end;
self = o;
}
return o;
}

View file

@ -53,10 +53,12 @@ NSSelectorFromString(NSString *aSelectorName)
{
if (aSelectorName != nil)
{
int len = [aSelectorName cStringLength];
int len = [aSelectorName length];
char buf[len+1];
[aSelectorName getCString: buf];
[aSelectorName getCString: buf
maxLength: len + 1
encoding: NSASCIIStringEncoding];
return GSSelectorFromName (buf);
}
return (SEL)0;
@ -71,10 +73,12 @@ NSClassFromString(NSString *aClassName)
{
if (aClassName != nil)
{
int len = [aClassName cStringLength];
int len = [aClassName length];
char buf[len+1];
[aClassName getCString: buf];
[aClassName getCString: buf
maxLength: len + 1
encoding: NSASCIIStringEncoding];
return GSClassFromName (buf);
}
return (Class)0;

View file

@ -216,12 +216,14 @@ serializeToInfo(id object, _NSSerializerInfo* info)
unsigned slen;
unsigned dlen;
slen = [object cStringLength] + 1;
slen = [object length] + 1;
(*info->appImp)(info->data, appSel, &st_cstring, 1);
(*info->serImp)(info->data, serSel, slen);
dlen = (*info->lenImp)(info->data, lenSel);
(*info->setImp)(info->data, setSel, dlen + slen);
[object getCString: (*info->datImp)(info->data, datSel) + dlen];
[object getCString: (*info->datImp)(info->data, datSel) + dlen
maxLength: slen
encoding: NSASCIIStringEncoding];
if (info->shouldUnique)
GSIMapAddPair(&info->map,
(GSIMapKey)object, (GSIMapVal)info->count++);

View file

@ -24,7 +24,8 @@
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111 USA.
Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
Boston, MA 02111 USA.
<title>NSString class reference</title>
$Date$ $Revision$
@ -165,8 +166,51 @@ static enum {
PH_WINDOWS
} pathHandling = PH_DO_THE_RIGHT_THING;
#define GSPathHandlingUnix() ((pathHandling == PH_UNIX) ? YES : NO)
#define GSPathHandlingWindows() ((pathHandling == PH_WINDOWS) ? YES : NO)
/**
* This function is intended to be called at startup (before anything else
* which needs to use paths, such as reading config files and user defaults)
* to allow a program to control the style of path handling required.<br />
* Almost all programs should avoid using this.<br />
* Changing the path handling mode is not thread-safe.<br />
* If mode is "windows" this sets path handling to be windows specific,<br />
* If mode is "unix" it sets path handling to be unix specific,<br />
* Any other none-null string sets do-the-right-thing mode.<br />
* The function returns a C String describing the old mode.
*/
const char*
GSPathHandling(const char *mode)
{
int old = pathHandling;
if (mode != 0)
{
if (strcasecmp(mode, "windows") == 0)
{
pathHandling = PH_WINDOWS;
}
else if (strcasecmp(mode, "unix") == 0)
{
pathHandling = PH_UNIX;
}
else
{
pathHandling = PH_DO_THE_RIGHT_THING;
}
}
switch (old)
{
case PH_WINDOWS: return "windows";
case PH_UNIX: return "unix";
default: return "right";
}
}
#define GSPathHandlingRight() \
((pathHandling == PH_DO_THE_RIGHT_THING) ? YES : NO)
#define GSPathHandlingUnix() \
((pathHandling == PH_UNIX) ? YES : NO)
#define GSPathHandlingWindows() \
((pathHandling == PH_WINDOWS) ? YES : NO)
/*
* The pathSeps character set is used for parsing paths ... it *must*
@ -181,26 +225,54 @@ pathSeps(void)
{
static NSCharacterSet *wPathSeps = nil;
static NSCharacterSet *uPathSeps = nil;
static NSCharacterSet *rPathSeps = nil;
if (GSPathHandlingRight())
{
if (rPathSeps == nil)
{
[placeholderLock lock];
if (rPathSeps == nil)
{
rPathSeps
= [NSCharacterSet characterSetWithCharactersInString: @"/\\"];
IF_NO_GC(RETAIN(rPathSeps));
}
[placeholderLock unlock];
}
return rPathSeps;
}
if (GSPathHandlingUnix())
{
if (uPathSeps == nil)
{
uPathSeps
= [NSCharacterSet characterSetWithCharactersInString: @"/"];
IF_NO_GC(RETAIN(uPathSeps));
[placeholderLock lock];
if (uPathSeps == nil)
{
uPathSeps
= [NSCharacterSet characterSetWithCharactersInString: @"/"];
IF_NO_GC(RETAIN(uPathSeps));
}
[placeholderLock unlock];
}
return uPathSeps;
}
else
if (GSPathHandlingWindows())
{
if (wPathSeps == nil)
{
wPathSeps
= [NSCharacterSet characterSetWithCharactersInString: @"/\\"];
IF_NO_GC(RETAIN(wPathSeps));
[placeholderLock lock];
if (wPathSeps == nil)
{
wPathSeps
= [NSCharacterSet characterSetWithCharactersInString: @"\\"];
IF_NO_GC(RETAIN(wPathSeps));
}
[placeholderLock unlock];
}
return wPathSeps;
}
pathHandling = PH_DO_THE_RIGHT_THING;
return pathSeps();
}
inline static BOOL
@ -208,11 +280,14 @@ pathSepMember(unichar c)
{
if (c == (unichar)'/')
{
return YES;
if (GSPathHandlingWindows() == NO)
{
return YES;
}
}
if (GSPathHandlingUnix() == NO)
else if (c == (unichar)'\\')
{
if (c == (unichar)'\\')
if (GSPathHandlingUnix() == NO)
{
return YES;
}
@ -220,48 +295,34 @@ pathSepMember(unichar c)
return NO;
}
/*
* For cross-platform portability we always use slash as the separator
* when building paths ... unless specific windows path handling is
* required.
*/
inline static unichar
pathSepChar()
{
#if defined(NATIVEPATHSEP)
#if defined(__MINGW32__)
if (GSPathHandlingUnix() == YES)
if (GSPathHandlingWindows() == NO)
{
return '/';
}
return '\\';
#else
if (GSPathHandlingWindows() == YES)
{
return '\\';
}
return '/';
#endif
#else
return '/';
#endif
}
/*
* For cross-platform portability we always use slash as the separator
* when building paths ... unless specific windows path handling is
* required.
*/
inline static NSString*
pathSepString()
{
#if defined(NATIVEPATHSEP)
#if defined(__MINGW32__)
if (GSPathHandlingUnix() == YES)
if (GSPathHandlingWindows() == NO)
{
return @"/";
}
return @"\\";
#else
if (GSPathHandlingWindows() == YES)
{
return @"\\";
}
return @"/";
#endif
#else
return @"/";
#endif
}
/*
@ -507,17 +568,6 @@ handle_printf_atsign (FILE *stream,
_DefaultStringEncoding = GetDefEncoding();
_ByteEncodingOk = GSIsByteEncoding(_DefaultStringEncoding);
if (getenv("GNUSTEP_PATH_HANDLING") != 0)
{
if (strcmp("unix", getenv("GNUSTEP_PATH_HANDLING")) == 0)
{
pathHandling = PH_UNIX;
}
else if (strcmp("windows", getenv("GNUSTEP_PATH_HANDLING")) == 0)
{
pathHandling = PH_WINDOWS;
}
}
NSStringClass = self;
[self setVersion: 1];
@ -621,22 +671,6 @@ handle_printf_atsign (FILE *stream,
return [NXConstantString class];
}
+ (void) setPathHandling: (NSString*)mode
{
pathHandling = PH_DO_THE_RIGHT_THING;
if (mode != nil)
{
if ([mode caseInsensitiveCompare: @"windows"] == NSOrderedSame)
{
pathHandling = PH_WINDOWS;
}
else if ([mode caseInsensitiveCompare: @"unix"] == NSOrderedSame)
{
pathHandling = PH_UNIX;
}
}
}
/**
* Create an empty string.
*/
@ -3039,10 +3073,8 @@ handle_printf_atsign (FILE *stream,
}
/**
* Retrieve the contents of the receiver into the buffer.<br />
* The buffer must be large enough to contain the CString representation
* of the characters in the receiver, plus a nul terminator which this
* method adds.
* Deprecated ... do not use.<br />.
* Use -getCString:maxLength:encoding: instead.
*/
- (void) getCString: (char*)buffer
{
@ -3052,9 +3084,8 @@ handle_printf_atsign (FILE *stream,
}
/**
* Retrieve up to maxLength bytes from the receiver into the buffer.<br />
* The buffer must be at least maxLength + 1 bytes long, so that it has
* room for the nul terminator that this method adds.
* Deprecated ... do not use.<br />.
* Use -getCString:maxLength:encoding: instead.
*/
- (void) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
@ -3066,34 +3097,58 @@ handle_printf_atsign (FILE *stream,
/**
* Retrieve up to maxLength bytes from the receiver into the buffer.<br />
* The buffer must be at least maxLength + 1 bytes long, so that it has
* room for the nul terminator that this method adds.
* In GNUstep, this method implements the actual behavior of the MacOS-X
* method rather than it's documented behavior ...<br />
* The maxLength argument must be the size (in bytes) of the area of
* memory pointed to by the buffer argument.<br />
* Returns YES on success.<br />
* Returns NO if maxLength is too small to hold the entire string
* including a terminating nul character.<br />
* If it returns NO, the terminating nul will <em>not</em> have been
* written to the buffer.<br />
* Raises an exception if the string can not be converted to the
* specified encoding without loss of information.<br />
* eg. If the receiver is @"hello" then the provided buffer must be
* at least six bytes long and the value of maxLength must be at least
* six if NSASCIIStringEncoding is requested, but they must be at least
* twelve if NSUnicodeStringEncoding is requested.
*/
- (void) getCString: (char*)buffer
- (BOOL) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
encoding: (NSStringEncoding)encoding
{
NSData *d = [self dataUsingEncoding: encoding];
unsigned len = [d length];
if (len > maxLength) len = maxLength;
memcpy(buffer, [d bytes], len);
if (encoding == NSUnicodeStringEncoding)
{
buffer[len++] = '\0';
unsigned length = [self length];
if (maxLength > length * sizeof(unichar))
{
unichar *ptr = (unichar*)buffer;
maxLength = (maxLength - 1) / sizeof(unichar);
[self getCharacters: ptr
range: NSMakeRange(0, maxLength)];
ptr[maxLength] = 0;
return YES;
}
return NO;
}
else
{
NSData *d = [self dataUsingEncoding: encoding];
unsigned length = [d length];
BOOL result = (length <= maxLength) ? YES : NO;
if (length > maxLength) length = maxLength;
memcpy(buffer, [d bytes], length);
buffer[length] = '\0';
return result;
}
buffer[len] = '\0';
}
/**
* Converts characters from the given range of the string to the c string
* encoding and stores the resulting bytes in the given buffer. As many
* characters are converted as will fit in the buffer. A trailing nul
* byte is always added, so the buffer needs to be big enough to hold
* maxLength+1 bytes.
* <br />
* If leftoverRange is non-NULL, the range of trailing characters that didn't
* will be stored in it.
* Deprecated ... do not use.<br />.
* Use -getCString:maxLength:encoding: instead.
*/
- (void) getCString: (char*)buffer
maxLength: (unsigned int)maxLength
@ -4419,27 +4474,15 @@ static NSFileManager *fm = nil;
{
s = AUTORELEASE([self mutableCopy]);
}
#if defined(NATIVEPATHSEP)
#if defined(__MINGW32__)
if (GSPathHandlingUnix() == YES)
{
[s replaceString: @"\\" withString: @"/"];
}
else
else if (GSPathHandlingWindows() == YES)
{
[s replaceString: @"/" withString: @"\\"];
}
#else
if (GSPathHandlingWindows() == YES)
{
[s replaceString: @"/" withString: @"\\"];
}
else
{
[s replaceString: @"\\" withString: @"/"];
}
#endif
#endif
l = [s length];
root = rootOf(s, l);

View file

@ -283,7 +283,7 @@ static NSString *_time_zone_path(NSString *subpath, NSString *type)
int offset; // Offset from UTC in seconds.
}
- (id) initWithOffset: (int)anOffset;
- (id) initWithOffset: (int)anOffset name: (NSString*)aName;
@end
@interface NSLocalTimeZone : NSTimeZone
@ -371,9 +371,51 @@ static NSString *_time_zone_path(NSString *subpath, NSString *type)
unichar c;
unsigned i;
if (length == 8 && [name hasPrefix: @"GMT"] == YES
if ((length == 3
&& ([name isEqualToString: @"GMT"] == YES
|| [name isEqualToString: @"UTC"] == YES
|| [name isEqualToString: @"UCT"] == YES))
|| (length == 4
&& ([name isEqualToString: @"GMT0"] == YES
|| [name isEqualToString: @"Zulu"] == YES))
|| (length == 9 && [name isEqualToString: @"Universal"] == YES))
{
// Synonyms for GMT
zone = [[GSAbsTimeZone alloc] initWithOffset: 0 name: name];
}
else if (length == 5 && [name hasPrefix: @"GMT"] == YES
&& ((c = [name characterAtIndex: 3]) == '+' || c == '-')
&& ((c = [name characterAtIndex: 4]) >= '0' && c <= '9'))
{
// GMT-9 to GMT+9
i = (c - '0') * 60 * 60;
if ([name characterAtIndex: 3] == '-')
{
i = -i;
}
zone = [[GSAbsTimeZone alloc] initWithOffset: i name: name];
}
else if (length == 6 && [name hasPrefix: @"GMT"] == YES
&& ((c = [name characterAtIndex: 3]) == '+' || c == '-')
&& ((c = [name characterAtIndex: 4]) == '0' || c == '1')
&& ((c = [name characterAtIndex: 5]) >= '0' && c <= '4'))
{
// GMT-14 to GMT-10 and GMT+10 to GMT+14
i = (c - '0') * 60 * 60;
if ([name characterAtIndex: 4] == '1')
{
i += 60 * 60 * 10;
}
if ([name characterAtIndex: 3] == '-')
{
i = -i;
}
zone = [[GSAbsTimeZone alloc] initWithOffset: i name: name];
}
else if (length == 8 && [name hasPrefix: @"GMT"] == YES
&& ((c = [name characterAtIndex: 3]) == '+' || c == '-'))
{
// GMT+NNNN and GMT-NNNN
c = [name characterAtIndex: 4];
if (c >= '0' && c <= '9')
{
@ -390,7 +432,13 @@ static NSString *_time_zone_path(NSString *subpath, NSString *type)
if (c >= '0' && c <= '9')
{
i = i * 10 + (c - '0');
zone = [[GSAbsTimeZone alloc] initWithOffset: i*60];
i = i * 60;
if ([name characterAtIndex: 3] == '-')
{
i = -i;
}
zone = [[GSAbsTimeZone alloc] initWithOffset: i
name: nil];
}
}
}
@ -402,7 +450,7 @@ static NSString *_time_zone_path(NSString *subpath, NSString *type)
{
i = [[name substringFromIndex: 19] intValue];
zone = [[GSAbsTimeZone alloc] initWithOffset: i];
zone = [[GSAbsTimeZone alloc] initWithOffset: i name: nil];
}
if (zone == nil)
@ -585,7 +633,7 @@ static NSMapTable *absolutes = 0;
[aCoder encodeObject: name];
}
- (id) initWithOffset: (int)anOffset
- (id) initWithOffset: (int)anOffset name: (NSString*)aName
{
GSAbsTimeZone *z;
int extra;
@ -630,25 +678,32 @@ static NSMapTable *absolutes = 0;
}
else
{
if (anOffset % 60 == 0)
if (aName == nil)
{
char s = (anOffset >= 0) ? '+' : '-';
int i = (anOffset >= 0) ? anOffset / 60 : -anOffset / 60;
int h = i / 60;
int m = i % 60;
char buf[9];
if (anOffset % 60 == 0)
{
char s = (anOffset >= 0) ? '+' : '-';
int i = (anOffset >= 0) ? anOffset / 60 : -anOffset / 60;
int h = i / 60;
int m = i % 60;
char buf[9];
sprintf(buf, "GMT%c%02d%02d", s, h, m);
name = [[NSString alloc] initWithUTF8String: buf];
sprintf(buf, "GMT%c%02d%02d", s, h, m);
name = [[NSString alloc] initWithUTF8String: buf];
}
else
{
/*
* Should never happen now we round to the minute
* for MacOS-X compatibnility.
*/
name = [[NSString alloc] initWithFormat: @"NSAbsoluteTimeZone:%d",
anOffset];
}
}
else
{
/*
* Should never happen now we round to the minute
* for MacOS-X compatibnility.
*/
name = [[NSString alloc] initWithFormat: @"NSAbsoluteTimeZone:%d",
anOffset];
name = [aName copy];
}
detail = [[GSAbsTimeZoneDetail alloc] initWithTimeZone: self];
offset = anOffset;
@ -1637,7 +1692,7 @@ static NSMapTable *absolutes = 0;
{
NSTimeZone *zone;
zone = [[GSAbsTimeZone alloc] initWithOffset: seconds];
zone = [[GSAbsTimeZone alloc] initWithOffset: seconds name: nil];
return AUTORELEASE(zone);
}

View file

@ -630,7 +630,7 @@ static unsigned urlAlign;
{
parsedURL *buf;
parsedURL *base = baseData;
unsigned size = [_urlString cStringLength];
unsigned size = [_urlString length];
char *end;
char *start;
char *ptr;
@ -643,7 +643,9 @@ static unsigned urlAlign;
buf = _data = (parsedURL*)NSZoneMalloc(GSAtomicMallocZone(), size);
memset(buf, '\0', size);
start = end = ptr = (char*)&buf[1];
[_urlString getCString: start];
[_urlString getCString: start
maxLength: size
encoding: NSASCIIStringEncoding];
/*
* Parse the scheme if possible.

View file

@ -102,7 +102,9 @@
@interface GSInet6InputStream : GSSocketInputStream
{
@private
#if defined(AF_INET6)
struct sockaddr_in6 _peerAddr;
#endif
}
/**
@ -184,7 +186,9 @@
@interface GSInet6OutputStream : GSSocketOutputStream
{
@private
#if defined(AF_INET6)
struct sockaddr_in6 _peerAddr;
#endif
}
/**
@ -742,7 +746,7 @@ static void setNonblocking(int fd)
@end
@implementation GSInet6InputStream
#if defined(AF_INET6)
- (socklen_t) sockLen
{
return sizeof(struct sockaddr_in6);
@ -770,7 +774,13 @@ static void setNonblocking(int fd)
}
return self;
}
#else
- (id) initToAddr: (NSString*)addr port: (int)port
{
RELEASE(self);
return nil;
}
#endif
@end
@implementation GSLocalInputStream
@ -1285,7 +1295,7 @@ static void setNonblocking(int fd)
@end
@implementation GSInet6OutputStream
#if defined(AF_INET6)
- (socklen_t) sockLen
{
return sizeof(struct sockaddr_in6);
@ -1313,7 +1323,13 @@ static void setNonblocking(int fd)
}
return self;
}
#else
- (id) initToAddr: (NSString*)addr port: (int)port
{
RELEASE(self);
return nil;
}
#endif
@end
@implementation GSLocalOutputStream
@ -1734,8 +1750,17 @@ static void setNonblocking(int fd)
if (acceptReturn < 0)
{ // test for real error
if (errno != EWOULDBLOCK && errno != ECONNABORTED
&& errno != EPROTO && errno != EINTR)
if (errno != EWOULDBLOCK
#if defined(EAGAIN)
&& errno != EAGAIN
#endif
#if defined(ECONNABORTED)
&& errno != ECONNABORTED
#endif
#if defined(EPROTO)
&& errno != EPROTO
#endif
&& errno != EINTR)
{
[self _recordError];
}
@ -1882,7 +1907,7 @@ static void setNonblocking(int fd)
@end
@implementation GSInet6ServerStream
#if defined(AF_INET6)
- (Class) _inputStreamClass
{
return [GSInet6InputStream class];
@ -1921,7 +1946,13 @@ static void setNonblocking(int fd)
NSAssert(_fd >= 0, @"cannot open socket");
return self;
}
#else
- (id) initToAddr: (NSString*)addr port: (int)port
{
RELEASE(self);
return nil;
}
#endif
@end
@implementation GSLocalServerStream