get base to compile again, and improve readability/consistency

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@34184 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
Richard Frith-MacDonald 2011-11-17 06:11:36 +00:00
parent 257cdd4a21
commit bc4151c775
3 changed files with 204 additions and 80 deletions

View file

@ -1,22 +1,35 @@
2011-11-17 Richard Frith-Macdonald <rfm@gnu.org>
* Source/GSString.m: Fix to compile again (use ifdef to consistently
have/not-have tiny strings), and tidy use of whitespace for readability
and coding standards.
I like the experimental tiny strings idea... will definitely save
space, but will need a lot of optimisation (like that of literal
strings) to stop it being slow.
Until it's about as fast as literal strings, we should probably only
enable it on platforms where memory footprint is an issue.
Not sure how to do that though.
2011-11-16 20:48 theraven
* libs/base/trunk/Source/GSString.m: Store tiny strings (up to 8
ASCII characters) inside the pointer. Strings of this length are fairly
common, and this makes them very cheap to store / copy / compare
(pointer comparisons test for equality). 8 characters seems to be enough
for quite a lot of common uses, such as path components and tokens.
There are possibly still some things constructing tiny strings and not
using these.
* Source/GSString.m: Store tiny strings (up to 8
ASCII characters) inside the pointer. Strings of this length are
fairly common, and this makes them very cheap to store/copy/compare
(pointer comparisons test for equality). 8 characters seems to be
enough for quite a lot of common uses, such as path components and
tokens.
There are possibly still some things constructing tiny strings and not
using these.
2011-11-16 17:29 theraven
* libs/base/trunk/Source/NSNumber.m: Implement the double boxing
techniques used by Smalltalk/X and Cincom Smalltalk. Now we can
conceal most doubles inside a pointer. This is most useful for
LanguageKit, but should save some memory / malloc overhead / heap
fragmentation in any code that uses a lot of NSNumbers (e.g.
anything that deals with big plists). OS X 10.7 employs a similar
trick.
* Source/NSNumber.m: Implement the double boxing
techniques used by Smalltalk/X and Cincom Smalltalk. Now we can
conceal most doubles inside a pointer. This is most useful for
LanguageKit, but should save some memory / malloc overhead / heap
fragmentation in any code that uses a lot of NSNumbers (e.g.
anything that deals with big plists). OS X 10.7 employs a similar
trick.
2011-11-15 Adam Fedor <fedor@gnu.org>

View file

@ -695,7 +695,7 @@ static void getCString_u(GSStr self, char *buffer, unsigned int maxLength,
#if defined(OBJC_SMALL_OBJECT_SHIFT) && (OBJC_SMALL_OBJECT_SHIFT == 3)
#define TINY_STRING_MASK 4
BOOL useTinyStrings;
static BOOL useTinyStrings;
/**
* A GSTinyString is used on 64-bit platforms to store up to 8 ASCII (7-bit)
* characters inside a pointer. Note that a mutable version of this class is
@ -718,17 +718,21 @@ BOOL useTinyStrings;
#define TINY_STRING_CHAR(s, x) ((s & (0xFE00000000000000 >> (x*7))) >> (57-(x*7)))
#define TINY_STRING_LENGTH_MASK 0x1f
#define TINY_STRING_LENGTH_SHIFT OBJC_SMALL_OBJECT_SHIFT
@interface GSTinyString : NSString @end
@interface GSTinyString : NSString
@end
@implementation GSTinyString
- (NSUInteger)length
- (NSUInteger) length
{
uintptr_t s = (uintptr_t)self;
return (s >> TINY_STRING_LENGTH_SHIFT) & TINY_STRING_LENGTH_MASK;
}
- (unichar)characterAtIndex: (NSUInteger)anIndex
- (unichar) characterAtIndex: (NSUInteger)anIndex
{
uintptr_t s = (uintptr_t)self;
NSUInteger length = (s >> TINY_STRING_LENGTH_SHIFT) & TINY_STRING_LENGTH_MASK;
if (anIndex >= length)
{
[NSException raise: NSInvalidArgumentException
@ -741,54 +745,82 @@ BOOL useTinyStrings;
}
return TINY_STRING_CHAR(s, anIndex);
}
+ (void)load
+ (void) load
{
useTinyStrings = objc_registerSmallObjectClass_np(self, TINY_STRING_MASK);
}
+ (id)alloc
+ (id) alloc
{
return (id)TINY_STRING_MASK;
}
+ (id)allocWithZone: (NSZone*)aZone
+ (id) allocWithZone: (NSZone*)aZone
{
return (id)TINY_STRING_MASK;
}
- (id)copy
- (id) copy
{
return self;
}
- (id)copyWithZone: (NSZone*)aZone
- (id) copyWithZone: (NSZone*)aZone
{
return self;
}
- (id)retain { return self; }
- (id)autorelease { return self; }
- (oneway void)release { }
- (id) retain
{
return self;
}
- (id) autorelease
{
return self;
}
- (oneway void) release
{
return;
}
@end
/**
* Constructs a tiny string.
*/
static id createTinyString(const char *str, int length)
static id
createTinyString(const char *str, int length)
{
// No tiny string support detected at run time, give up
if (!useTinyStrings) { return nil; }
// String too long to fit in a pointer, give up
if (length > 9) { return nil; }
// String would fit if the last byte was an implicit 0, but it isn't.
if ((length == 9) && str[8] != '\0') { return nil; }
/* No tiny string support detected at run time, give up
*/
if (!useTinyStrings)
{
return nil;
}
/* String too long to fit in a pointer, give up
*/
if (length > 9)
{
return nil;
}
/* String would fit if the last byte was an implicit 0, but it isn't.
*/
if ((length == 9) && str[8] != '\0')
{
return nil;
}
uintptr_t s = TINY_STRING_MASK;
s |= length << TINY_STRING_LENGTH_SHIFT;
for (unsigned int i = 0 ; i<length ; i++)
{
s |= ((uintptr_t)str[i]) << (57 - (i*7));
}
{
s |= ((uintptr_t)str[i]) << (57 - (i*7));
}
return (id)s;
}
#else
static id createTinyString(const char *str, int length)
{
return nil;
}
#endif
/*
* The GSPlaceholderString class is used by the abstract cluster root
@ -945,11 +977,13 @@ fixBOM(unsigned char **bytes, NSUInteger*length, BOOL *owned,
{
const void *original = bytes;
#if defined(OBJC_SMALL_OBJECT_SHIFT) && (OBJC_SMALL_OBJECT_SHIFT == 3)
if (useTinyStrings)
{
if (NSASCIIStringEncoding == encoding)
{
id tinyString = createTinyString(bytes, length);
if (tinyString)
{
return tinyString;
@ -958,7 +992,8 @@ fixBOM(unsigned char **bytes, NSUInteger*length, BOOL *owned,
if (NSUTF8StringEncoding == encoding && (length < 9))
{
NSUInteger i;
for (i=0 ; i<length ; i++)
for (i = 0; i < length; i++)
{
if (((const char*)bytes)[i] & 0x80)
{
@ -968,6 +1003,7 @@ fixBOM(unsigned char **bytes, NSUInteger*length, BOOL *owned,
if (i == length)
{
id tinyString = createTinyString(bytes, length);
if (tinyString)
{
return tinyString;
@ -975,6 +1011,7 @@ fixBOM(unsigned char **bytes, NSUInteger*length, BOOL *owned,
}
}
}
#endif
fixBOM((unsigned char**)&bytes, &length, &flag, encoding);
/*

View file

@ -357,46 +357,71 @@ static BOOL useSmallRepeatingDouble;
#define SMALL_REPEATING_DOUBLE_MASK 3
@interface NSSmallInt : NSSignedIntegerNumber @end
@interface NSSmallInt : NSSignedIntegerNumber
@end
@implementation NSSmallInt
#undef VALUE
#define VALUE (((intptr_t)self) >> OBJC_SMALL_OBJECT_SHIFT)
#define FORMAT @"%d"
#include "NSNumberMethods.h"
+ (void)load
+ (void) load
{
useSmallInt = objc_registerSmallObjectClass_np(self, SMALL_INT_MASK);
}
+ (id)alloc
+ (id) alloc
{
return (id)1;
}
+ (id)allocWithZone: (NSZone*)aZone
+ (id) allocWithZone: (NSZone*)aZone
{
return (id)1;
}
- (id)copy
- (id) copy
{
return self;
}
- (id)copyWithZone: (NSZone*)aZone
- (id) copyWithZone: (NSZone*)aZone
{
return self;
}
- (id)retain { return self; }
- (id)autorelease { return self; }
- (oneway void)release { }
- (id) retain
{
return self;
}
- (id) autorelease
{
return self;
}
- (oneway void) release
{
return;
}
@end
#if OBJC_SMALL_OBJECT_SHIFT == 3
union BoxedDouble
{
id obj;
uintptr_t bits;
double d;
} ;
@interface NSSmallExtendedDouble : NSFloatingPointNumber @end
id obj;
uintptr_t bits;
double d;
};
@interface NSSmallExtendedDouble : NSFloatingPointNumber
@end
@implementation NSSmallExtendedDouble
static double unboxSmallExtendedDouble(uintptr_t boxed)
static double
unboxSmallExtendedDouble(uintptr_t boxed)
{
// The low bit of the mantissa
uintptr_t mask = boxed & 8;
@ -406,12 +431,16 @@ static double unboxSmallExtendedDouble(uintptr_t boxed)
ret.bits = boxed | (mask >> 1) | (mask >> 2) | (mask >> 3);
return ret.d;
}
static BOOL isSmallExtendedDouble(double d)
static BOOL
isSmallExtendedDouble(double d)
{
union BoxedDouble b = {.d=d};
return unboxSmallExtendedDouble(b.bits) == d;
}
static double unboxSmallRepeatingDouble(uintptr_t boxed)
static double
unboxSmallRepeatingDouble(uintptr_t boxed)
{
// The low bit of the mantissa
uintptr_t mask = boxed & 56;
@ -421,75 +450,120 @@ static double unboxSmallRepeatingDouble(uintptr_t boxed)
ret.bits = boxed | (mask >> 3);
return ret.d;
}
static BOOL isSmallRepeatingDouble(double d)
static BOOL
isSmallRepeatingDouble(double d)
{
union BoxedDouble b = {.d=d};
return unboxSmallRepeatingDouble(b.bits) == d;
}
static id boxDouble(double d, uintptr_t mask)
static id
boxDouble(double d, uintptr_t mask)
{
union BoxedDouble b = {.d=d};
b.bits &= ~OBJC_SMALL_OBJECT_MASK;
b.bits |= mask;
return b.obj;
}
#undef VALUE
#define VALUE (unboxSmallExtendedDouble((uintptr_t)self))
#define FORMAT @"%0.16g"
#include "NSNumberMethods.h"
+ (void)load
+ (void)
load
{
useSmallExtendedDouble = objc_registerSmallObjectClass_np(self, SMALL_EXTENDED_DOUBLE_MASK);
useSmallExtendedDouble = objc_registerSmallObjectClass_np
(self, SMALL_EXTENDED_DOUBLE_MASK);
}
+ (id)alloc
+ (id) alloc
{
return (id)SMALL_EXTENDED_DOUBLE_MASK;
}
+ (id)allocWithZone: (NSZone*)aZone
+ (id) allocWithZone: (NSZone*)aZone
{
return (id)SMALL_EXTENDED_DOUBLE_MASK;
}
- (id)copy
- (id) copy
{
return self;
}
- (id)copyWithZone: (NSZone*)aZone
- (id) copyWithZone: (NSZone*)aZone
{
return self;
}
- (id)retain { return self; }
- (id)autorelease { return self; }
- (oneway void)release { }
- (id) retain
{
return self;
}
- (id) autorelease
{
return self;
}
- (oneway void) release
{
return;
}
@end
@interface NSSmallRepeatingDouble : NSFloatingPointNumber @end
@interface NSSmallRepeatingDouble : NSFloatingPointNumber
@end
@implementation NSSmallRepeatingDouble
#undef VALUE
#define VALUE (unboxSmallRepeatingDouble((uintptr_t)self))
#define FORMAT @"%0.16g"
#include "NSNumberMethods.h"
+ (void)load
+ (void) load
{
useSmallRepeatingDouble = objc_registerSmallObjectClass_np(self, SMALL_REPEATING_DOUBLE_MASK);
useSmallRepeatingDouble = objc_registerSmallObjectClass_np
(self, SMALL_REPEATING_DOUBLE_MASK);
}
+ (id)alloc
+ (id) alloc
{
return (id)SMALL_REPEATING_DOUBLE_MASK;
}
+ (id)allocWithZone: (NSZone*)aZone
+ (id) allocWithZone: (NSZone*)aZone
{
return (id)SMALL_REPEATING_DOUBLE_MASK;
}
- (id)copy
- (id) copy
{
return self;
}
- (id)copyWithZone: (NSZone*)aZone
- (id) copyWithZone: (NSZone*)aZone
{
return self;
}
- (id)retain { return self; }
- (id)autorelease { return self; }
- (oneway void)release { }
- (id) retain
{
return self;
}
- (id) autorelease
{
return self;
}
- (oneway void) release
{
return;
}
@end
#endif
#endif