Index: src/OFString.h ================================================================== --- src/OFString.h +++ src/OFString.h @@ -365,10 +365,19 @@ * * \return An OFNumber */ - (uintmax_t)hexadecimalValueAsInteger; +/** + * Returns the string as an array of of_unichar_t. The result needs to be + * free()'d by the caller, as the memory is not marked as belonging to the + * object. + * + * \return The string as an array of Unicode characters + */ +- (of_unichar_t*)unicodeString; + /** * Writes the string into the specified file using UTF-8 encoding. * * \param path The path of the file to write to */ Index: src/OFString.m ================================================================== --- src/OFString.m +++ src/OFString.m @@ -1024,10 +1024,42 @@ num = newnum; } return num; } + +- (of_unichar_t*)unicodeString +{ + of_unichar_t *ret; + size_t i, j, len; + + len = [self length]; + + if ((ret = malloc((len + 1) * sizeof(of_unichar_t))) == NULL) + @throw [OFOutOfMemoryException newWithClass: isa]; + + i = j = 0; + + while (i < length) { + of_unichar_t c; + size_t clen; + + clen = of_string_utf8_to_unicode(string + i, length - 1, &c); + + if (clen == 0 || c > 0x10FFFF) { + free(ret); + @throw [OFInvalidEncodingException newWithClass: isa]; + } + + ret[j++] = c; + i += clen; + } + + ret[j] = 0; + + return ret; +} - (void)writeToFile: (OFString*)path { OFAutoreleasePool *pool = [[OFAutoreleasePool alloc] init]; OFFile *file; Index: tests/OFStringTests.m ================================================================== --- tests/OFStringTests.m +++ tests/OFStringTests.m @@ -8,10 +8,13 @@ * Q Public License 1.0, which can be found in the file LICENSE included in * the packaging of this file. */ #include "config.h" + +#include +#include #import "OFString.h" #import "OFArray.h" #import "OFAutoreleasePool.h" #import "OFExceptions.h" @@ -21,10 +24,11 @@ static OFString *module = @"OFString"; static OFString* whitespace[] = { @" \r \t\n\t \tasd \t \t\t\r\n", @" \t\t \t\t \t \t" }; +static of_unichar_t ucstr[] = { 'f', 0xF6, 0xF6, 'b', 0xE4, 'r', 0 }; @interface EntityHandler: OFObject @end @implementation EntityHandler @@ -43,10 +47,11 @@ { OFAutoreleasePool *pool = [[OFAutoreleasePool alloc] init]; OFMutableString *s[3]; OFArray *a; int i; + of_unichar_t *ua; EntityHandler *h; s[0] = [OFMutableString stringWithString: @"täs€"]; s[1] = [OFMutableString string]; s[2] = [[s[0] copy] autorelease]; @@ -250,10 +255,13 @@ EXPECT_EXCEPTION(@"Detect out of range in -[hexadecilamValueAsInteger", OFOutOfRangeException, [@"0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF" @"0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF" hexadecimalValueAsInteger]) + + TEST(@"-[unicodeString]", (ua = [@"fööbär" unicodeString]) && + !memcmp(ua, ucstr, 7 * sizeof(of_unichar_t)) && R(free(ua))) TEST(@"-[md5Hash]", [[@"asdfoobar" md5Hash] isEqual: @"184dce2ec49b5422c7cfd8728864db4c"]) TEST(@"-[sha1Hash]", [[@"asdfoobar" sha1Hash]