summaryrefslogtreecommitdiff
path: root/sal/rtl/source/ustring.c
diff options
context:
space:
mode:
authorJens-Heiner Rechtien <hr@openoffice.org>2000-09-18 14:18:43 +0000
committerJens-Heiner Rechtien <hr@openoffice.org>2000-09-18 14:18:43 +0000
commit9399c662f36c385b0c705eb34e636a9aec450282 (patch)
treef502e9d9258960ff214ab90e98e31d0075e60196 /sal/rtl/source/ustring.c
initial import
Diffstat (limited to 'sal/rtl/source/ustring.c')
-rw-r--r--sal/rtl/source/ustring.c1774
1 files changed, 1774 insertions, 0 deletions
diff --git a/sal/rtl/source/ustring.c b/sal/rtl/source/ustring.c
new file mode 100644
index 000000000000..fe97fedb7aa2
--- /dev/null
+++ b/sal/rtl/source/ustring.c
@@ -0,0 +1,1774 @@
+/*************************************************************************
+ *
+ * $RCSfile: ustring.c,v $
+ *
+ * $Revision: 1.1.1.1 $
+ *
+ * last change: $Author: hr $ $Date: 2000-09-18 15:17:24 $
+ *
+ * The Contents of this file are made available subject to the terms of
+ * either of the following licenses
+ *
+ * - GNU Lesser General Public License Version 2.1
+ * - Sun Industry Standards Source License Version 1.1
+ *
+ * Sun Microsystems Inc., October, 2000
+ *
+ * GNU Lesser General Public License Version 2.1
+ * =============================================
+ * Copyright 2000 by Sun Microsystems, Inc.
+ * 901 San Antonio Road, Palo Alto, CA 94303, USA
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License version 2.1, as published by the Free Software Foundation.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ *
+ *
+ * Sun Industry Standards Source License Version 1.1
+ * =================================================
+ * The contents of this file are subject to the Sun Industry Standards
+ * Source License Version 1.1 (the "License"); You may not use this file
+ * except in compliance with the License. You may obtain a copy of the
+ * License at http://www.openoffice.org/license.html.
+ *
+ * Software provided under this License is provided on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
+ * WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
+ * MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
+ * See the License for the specific provisions governing your rights and
+ * obligations concerning the Software.
+ *
+ * The Initial Developer of the Original Code is: Sun Microsystems, Inc.
+ *
+ * Copyright: 2000 by Sun Microsystems, Inc.
+ *
+ * All Rights Reserved.
+ *
+ * Contributor(s): _______________________________________
+ *
+ *
+ ************************************************************************/
+
+#ifndef _OSL_INTERLOCK_H_
+#include <osl/interlck.h>
+#endif
+
+#ifndef _OSL_DIAGNOSE_H_
+#include <osl/diagnose.h>
+#endif
+
+#ifndef _SAL_CONFIG_H_
+#include <sal/config.h>
+#endif
+
+#ifndef _RTL_CHAR_H_
+#include <rtl/char.h>
+#endif
+
+#ifndef _RTL_USTRING_H_
+#include <rtl/ustring.h>
+#endif
+
+#ifndef _RTL_USTRING_
+#include <rtl/ustring>
+#endif
+
+#ifndef _RTL_LOCALE_H_
+#include <rtl/locale.h>
+#endif
+
+#ifndef _RTL_MEMORY_H_
+#include <rtl/memory.h>
+#endif
+
+#ifndef _RTL_ALLOC_H_
+#include <rtl/alloc.h>
+#endif
+
+#ifndef _RTL_TEXTCVT_H
+#include <rtl/textcvt.h>
+#endif
+
+#ifndef _RTL_TENCINFO_H
+#include <rtl/tencinfo.h>
+#endif
+
+#include <math.h>
+
+
+static sal_Char const RTL_STR_DIGITS[] =
+{
+ '0' , '1' , '2' , '3' , '4' , '5' ,
+ '6' , '7' , '8' , '9' , 'a' , 'b' ,
+ 'c' , 'd' , 'e' , 'f' , 'g' , 'h' ,
+ 'i' , 'j' , 'k' , 'l' , 'm' , 'n' ,
+ 'o' , 'p' , 'q' , 'r' , 's' , 't' ,
+ 'u' , 'v' , 'w' , 'x' , 'y' , 'z'
+};
+
+/* static data to be referenced by all empty strings
+ * the refCount is predefined to 1 and must never become 0 !
+ */
+static rtl_uString aEmpty_rtl_wString =
+{
+ 1, /* sal_Int32 refCount; */
+ 0, /* sal_Int32 length; */
+ 0 /* sal_Unicode buffer[1]; */
+};
+
+/*************************************************************************
+ * rtl_ustr_getLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_getLength( const sal_Unicode * str )
+{
+ const sal_Unicode * pTempStr = str;
+ while( *pTempStr ) pTempStr++;
+ return pTempStr - str;
+}
+
+/*************************************************************************
+ * rtl_ustr_equalsIgnoreCase_WithLength
+ */
+sal_Bool SAL_CALL rtl_ustr_equalsIgnoreCase_WithLength( const sal_Unicode * first,
+ sal_Int32 firstLen,
+ const sal_Unicode * second,
+ sal_Int32 secondLen )
+{
+ sal_Unicode a;
+ sal_Unicode b;
+
+ if (firstLen != secondLen)
+ return sal_False;
+
+ while ( firstLen )
+ {
+ a = rtl_char_toUpperCase(*first);
+ b = rtl_char_toUpperCase(*second);
+
+ /* Naechstes Zeichen */
+ first++;
+ second++;
+ firstLen--;
+
+ /* If characters don't match but case may be ignored,
+ try converting both characters to uppercase.
+ If the results match, then the comparison scan should
+ continue. */
+ if ( a == b )
+ continue;
+
+ /* Unfortunately, conversion to uppercase does not work properly
+ for the Georgian alphabet, which has strange rules about case
+ conversion. So we need to make one last check before
+ exiting. */
+ if ( rtl_char_toLowerCase(a) == rtl_char_toLowerCase(b) )
+ continue;
+
+ return sal_False;
+ }
+
+ return sal_True; /* Strings sind gleich */
+}
+
+/*************************************************************************
+ * rtl_ustr_equalsIgnoreCase
+ */
+sal_Bool SAL_CALL rtl_ustr_equalsIgnoreCase( const sal_Unicode * first, const sal_Unicode * second )
+{
+ return rtl_ustr_equalsIgnoreCase_WithLength( first, rtl_ustr_getLength(first),
+ second, rtl_ustr_getLength(second) );
+}
+
+/*************************************************************************
+ * rtl_ustr_compare_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_compare_WithLength( const sal_Unicode * first,
+ sal_Int32 firstLen,
+ const sal_Unicode * second,
+ sal_Int32 secondLen )
+{
+ const sal_Unicode * firstEnd = first + firstLen;
+ const sal_Unicode * secondEnd = second + secondLen;
+ sal_Int32 nResult = 0;
+ while( first < firstEnd && second < secondEnd
+ && (0 == (nResult = (sal_Int32)*first++ - (sal_Int32)*second++ ) ) )
+ ;
+ if( nResult )
+ return nResult;
+ return firstLen - secondLen;
+}
+
+/*************************************************************************
+ * rtl_ustr_compare_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_shortenedCompare_WithLength( const sal_Unicode * first,
+ sal_Int32 firstLen,
+ const sal_Unicode * second,
+ sal_Int32 secondLen,
+ sal_Int32 shortenedLength )
+{
+ const sal_Unicode * firstEnd = first + firstLen;
+ const sal_Unicode * secondEnd = second + secondLen;
+ sal_Int32 nResult = 0;
+ while( shortenedLength-- && first < firstEnd && second < secondEnd
+ && (0 == (nResult = (sal_Int32)*first++ - (sal_Int32)*second++ ) ) )
+ ;
+ if( nResult || !(shortenedLength != -1) )
+ return nResult;
+ return firstLen - secondLen;
+}
+
+/*************************************************************************
+ * rtl_ustr_compare
+ */
+sal_Int32 SAL_CALL rtl_ustr_compare( const sal_Unicode * first, const sal_Unicode * second )
+{
+ sal_Int32 nRet;
+ while ( ((nRet = ((sal_Int32)*first)-((sal_Int32)*second)) == 0) &&
+ *second )
+ {
+ first++;
+ second++;
+ }
+
+ return nRet;
+}
+
+/*************************************************************************
+ * rtl_ustr_ascii_compare_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_ascii_compare_WithLength( const sal_Unicode * first,
+ sal_Int32 firstLen,
+ const sal_Char * second )
+{
+ return rtl_ustr_ascii_shortenedCompare_WithLength( first, firstLen, second, 0x7FFFFFF );
+}
+
+/*************************************************************************
+ * rtl_ustr_ascii_compare
+ */
+sal_Int32 SAL_CALL rtl_ustr_ascii_compare( const sal_Unicode * first, const sal_Char * second )
+{
+ sal_Int32 nRet;
+ while ( ((nRet = ((sal_Int32)*first)-((sal_Int32)*second)) == 0) &&
+ *second )
+ {
+ first++;
+ second++;
+ }
+
+ return nRet;
+}
+
+/*************************************************************************
+ * rtl_ustr_ascii_shortenedCompare_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_ascii_shortenedCompare_WithLength( const sal_Unicode * first,
+ sal_Int32 firstLen,
+ const sal_Char * second,
+ sal_Int32 shortenedLength )
+{
+ const sal_Unicode * firstEnd = first + firstLen;
+ sal_Int32 nResult = 0;
+ while( shortenedLength--
+ && first < firstEnd
+ && *second // necessary if 0 is allowed in Unicode
+ && (0 == (nResult = (sal_Int32)*first++ - (sal_Int32)*second++ ) ) )
+ {
+ /* Check ASCII range */
+ OSL_ENSHURE( (*(second-1) & 0x80) == 0, "Found ASCII char > 127");
+ }
+ if( !nResult && (shortenedLength != -1) )
+ {
+ if( *second )
+ {
+ OSL_ENSHURE( first == firstEnd, "first == firstEnd failed" );
+ // first is a substring of the second string => less (negative value)
+ nResult = -1;
+ }
+ else
+ // greater or equal
+ nResult = firstEnd - first;
+ }
+
+ return nResult;
+}
+
+/*************************************************************************
+ * rtl_ustr_asciil_reverseCompare_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_asciil_reverseCompare_WithLength( const sal_Unicode * first, sal_Int32 firstLen,
+ const sal_Char * second, sal_Int32 secondLen )
+{
+ const sal_Unicode * firstRun = first + firstLen;
+ const sal_Char * secondRun = second + secondLen;
+ sal_Int32 nResult = 0;
+ while( first < firstRun && second < secondRun
+ && (0 == (nResult = (sal_Int32)*--firstRun - (sal_Int32)*--secondRun ) ) )
+ ;
+ if( nResult )
+ return nResult;
+ return firstLen - secondLen;
+}
+
+
+/*************************************************************************
+ * rtl_ustr_hashCode_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_hashCode_WithLength( const sal_Unicode * str, sal_Int32 len )
+{
+ sal_Int32 h = 0;
+ const sal_Unicode * pVal = str;
+ sal_Int32 length = len;
+
+ if( length < 16 )
+ {
+ while( *pVal )
+ h = (h * 37) + *pVal++;
+ }
+ else
+ {
+ sal_Int32 off = 0;
+ sal_Int32 i;
+ /* only sample some characters */
+ sal_Int32 skip = length / 8;
+ for( i = length ; i > 0; i -= skip, off += skip )
+ {
+ h = (h * 39) + pVal[off];
+ }
+ }
+
+ return h;
+}
+
+/*************************************************************************
+ * rtl_ustr_hashCode
+ */
+sal_Int32 SAL_CALL rtl_ustr_hashCode( const sal_Unicode * str )
+{
+ return rtl_ustr_hashCode_WithLength(str, rtl_ustr_getLength(str));
+}
+
+/*************************************************************************
+ * rtl_ustr_indexOfChar_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_indexOfChar_WithLength( const sal_Unicode * str,
+ sal_Int32 len,
+ sal_Unicode ch )
+{
+ sal_Int32 index = 0;
+
+ while ( index != len )
+ {
+ if (!(*str))
+ return -1;;
+
+ if ( *str == ch )
+ /* Zeichen gefunden */
+ return index;
+
+ /* Naechstes Zeichen */
+ index++;
+ str++;
+ }
+
+ /* Zeichen nicht gefunden */
+ return -1;
+}
+
+/*************************************************************************
+ * rtl_ustr_indexOfChar
+ */
+sal_Int32 SAL_CALL rtl_ustr_indexOfChar( const sal_Unicode * str, sal_Unicode ch )
+{
+ return rtl_ustr_indexOfChar_WithLength(str, rtl_ustr_getLength(str), ch);
+}
+
+/*************************************************************************
+ * rtl_ustr_lastIndexOfChar_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_lastIndexOfChar_WithLength( const sal_Unicode * str,
+ sal_Int32 len,
+ sal_Unicode ch )
+{
+ sal_Int32 index = len - 1;
+
+ while ( index >= 0 )
+ {
+ if ( *(str + index) == ch )
+ /* Zeichen gefunden */
+ return index;
+
+ /* Naechstes Zeichen */
+ index--;
+ }
+
+ /* Zeichen nicht gefunden */
+ return -1;
+}
+
+/*************************************************************************
+ * rtl_ustr_lastIndexOfChar
+ */
+sal_Int32 SAL_CALL rtl_ustr_lastIndexOfChar( const sal_Unicode * str, sal_Unicode ch )
+{
+ return rtl_ustr_lastIndexOfChar_WithLength(str, rtl_ustr_getLength(str), ch);
+}
+
+/*************************************************************************
+ * rtl_ustr_indexOfStr_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_indexOfStr_WithLength( const sal_Unicode * str,
+ sal_Int32 len,
+ const sal_Unicode * subStr,
+ sal_Int32 subLen )
+{
+ sal_Int32 index = 0;
+
+ if (len < subLen)
+ return -1;
+
+ while ( *str )
+ {
+ if ( *str == *subStr)
+ {
+ sal_Int32 offset = 0;
+
+ /* wenn die restliche Laenge kleiner als der zu suchende string ist
+ kann der nicht mehr gefunden werden */
+ if ((len - index) < subLen)
+ return -1;
+
+ while ( offset != subLen)
+ {
+ if ( *(str + offset) != *(subStr + offset))
+ break;
+
+ offset++;
+ }
+
+ /* Schleife komplett durchlaufen, d.h. string gefunden */
+ if ( offset == subLen)
+ return index;
+ }
+
+ index++;
+ str++;
+ }
+
+ return -1;
+}
+
+/*************************************************************************
+ * rtl_ustr_indexOfStr
+ */
+sal_Int32 SAL_CALL rtl_ustr_indexOfStr( const sal_Unicode * str, const sal_Unicode * subStr )
+{
+ return rtl_ustr_indexOfStr_WithLength( str, rtl_ustr_getLength(str),
+ subStr, rtl_ustr_getLength(subStr) );
+}
+
+/*************************************************************************
+ * rtl_ustr_lastIndexOfStr_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_lastIndexOfStr_WithLength( const sal_Unicode * pSource,
+ sal_Int32 len,
+ const sal_Unicode * pSearch,
+ sal_Int32 nSearchLen )
+{
+ const sal_Unicode * pRunSource = pSource + len -1;
+ while( pRunSource >= pSource && pRunSource - pSource >= nSearchLen )
+ {
+ const sal_Unicode * pRunSearch = pSearch + nSearchLen -1;
+ const sal_Unicode * pSaveRunSource = pRunSource;
+ while( pRunSearch >= pSearch && *(pRunSearch--) == *(pRunSource--) )
+ ;
+ if( pRunSearch < pSearch )
+ return pRunSource - pSource +1;
+ pRunSource = pSaveRunSource;
+ pRunSource--;
+ }
+ return -1;
+}
+
+/*************************************************************************
+ * rtl_ustr_lastIndexOfStrPtr
+ */
+sal_Int32 SAL_CALL rtl_ustr_lastIndexOfStr( const sal_Unicode * str, const sal_Unicode * subStr )
+{
+ return rtl_ustr_lastIndexOfStr_WithLength( str, rtl_ustr_getLength(str),
+ subStr, rtl_ustr_getLength(subStr) );
+}
+
+/*************************************************************************
+ * rtl_ustr_replaceChar_WithLength
+ */
+void SAL_CALL rtl_ustr_replaceChar_WithLength( sal_Unicode * str,
+ sal_Int32 len,
+ sal_Unicode oldChar,
+ sal_Unicode newChar)
+{
+ while ( *str )
+ {
+ if ( *str == oldChar)
+ *str = newChar;
+
+ str++;
+ }
+}
+
+/*************************************************************************
+ * rtl_ustr_replaceChar
+ */
+void SAL_CALL rtl_ustr_replaceChar( sal_Unicode * str, sal_Unicode oldChar, sal_Unicode newChar)
+{
+ while ( *str )
+ {
+ if ( *str == oldChar)
+ *str = newChar;
+
+ str++;
+ }
+}
+
+/*************************************************************************
+ * rtl_ustr_toAsciiLowerCase_WithLength
+ */
+void SAL_CALL rtl_ustr_toAsciiLowerCase_WithLength( sal_Unicode * str, sal_Int32 len )
+{
+ sal_Unicode ch;
+
+ while ( *str )
+ {
+ ch = *str;
+ *str = rtl_char_toLowerCase(ch);
+ str++;
+ }
+}
+
+/*************************************************************************
+ * rtl_ustr_toAsciiLowerCase
+ */
+void SAL_CALL rtl_ustr_toAsciiLowerCase( sal_Unicode * str )
+{
+ sal_Unicode ch;
+
+ while ( *str )
+ {
+ ch = *str;
+ *str = rtl_char_toLowerCase(ch);
+ str++;
+ }
+}
+
+/*************************************************************************
+ * rtl_ustr_toAsciiUpperCase_WithLength
+ */
+void SAL_CALL rtl_ustr_toAsciiUpperCase_WithLength(sal_Unicode * str, sal_Int32 len)
+{
+ sal_Unicode ch;
+
+ while ( *str )
+ {
+ ch = *str;
+ *str = rtl_char_toUpperCase(ch);
+ str++;
+ }
+}
+
+/*************************************************************************
+ * rtl_ustr_toAsciiUpperCase
+ */
+void SAL_CALL rtl_ustr_toAsciiUpperCase(sal_Unicode * str)
+{
+ sal_Unicode ch;
+
+ while ( *str )
+ {
+ ch = *str;
+ *str = rtl_char_toUpperCase(ch);
+ str++;
+ }
+}
+
+/*************************************************************************
+ * rtl_ustr_trim_WithLength
+ */
+sal_Int32 SAL_CALL rtl_ustr_trim_WithLength( sal_Unicode * str, sal_Int32 len )
+{
+ sal_Int32 preSpaces = 0;
+ sal_Int32 postSpaces = 0;
+ sal_Int32 newLen = 0;
+ sal_Int32 index = len - 1;
+
+ while ( (preSpaces < len) && rtl_char_isWhitespace(*(str+preSpaces)) )
+ preSpaces++;
+
+ while ( (index > preSpaces) && rtl_char_isWhitespace(*(str+index)) )
+ {
+ postSpaces++;
+ index--;
+ }
+
+ newLen = len - preSpaces - postSpaces;
+
+ if ( newLen != len )
+ {
+ sal_Unicode *newStr = str + preSpaces;
+ index = 0;
+
+ while ( index != newLen )
+ {
+ *(str + index) = *(newStr + index);
+ index++;
+ }
+ *(str + index) = 0;
+ }
+
+ return newLen;
+}
+
+/*************************************************************************
+ * rtl_ustr_trim
+ */
+sal_Int32 SAL_CALL rtl_ustr_trim( sal_Unicode * str )
+{
+ return rtl_ustr_trim_WithLength(str, rtl_ustr_getLength(str));
+}
+
+/*************************************************************************
+ * rtl_ustr_valueOfosl_BOOL
+ */
+sal_Int32 SAL_CALL rtl_ustr_valueOfBoolean( sal_Unicode * str, sal_Bool b )
+{
+ if (b)
+ {
+ sal_Unicode *tmpStr = L"True";
+ rtl_copyMemory(str, tmpStr, 5 * sizeof(sal_Unicode));
+ return 4;
+ } else
+ {
+ sal_Unicode *tmpStr = L"False";
+ rtl_copyMemory(str, tmpStr, 6 * sizeof(sal_Unicode));
+ return 5;
+ }
+}
+
+/*************************************************************************
+ * rtl_ustr_valueOfChar
+ */
+sal_Int32 SAL_CALL rtl_ustr_valueOfChar( sal_Unicode * str, sal_Unicode ch )
+{
+ str[0] = ch;
+ str[1] = L'\0';
+ return 1;
+}
+
+/*************************************************************************
+ * rtl_ustr_valueOfosl_INT32
+ */
+sal_Int32 SAL_CALL rtl_ustr_valueOfInt32(sal_Unicode * str, sal_Int32 i, sal_Int16 radix )
+{
+ sal_Unicode buf[RTL_USTR_MAX_VALUEOFINT32];
+ sal_Bool negative = (i < 0);
+ sal_Int32 charPos = RTL_USTR_MAX_VALUEOFINT32 - 1;
+
+ if (radix < RTL_USTR_MIN_RADIX || radix > RTL_USTR_MAX_RADIX)
+ radix = 10;
+
+ if (!negative) {
+ i = -i;
+ }
+
+ while (i <= -radix) {
+ buf[charPos--] = RTL_STR_DIGITS[-(i % radix)];
+ i = i / radix;
+ }
+ buf[charPos] = RTL_STR_DIGITS[-i];
+
+ if (negative) {
+ buf[--charPos] = '-';
+ }
+
+ rtl_copyMemory(str, buf + charPos, (RTL_USTR_MAX_VALUEOFINT32 - charPos) * sizeof(sal_Unicode));
+
+ return (RTL_USTR_MAX_VALUEOFINT32 - charPos);
+}
+
+/*************************************************************************
+ * rtl_ustr_valueOfosl_INT64
+ */
+sal_Int32 SAL_CALL rtl_ustr_valueOfInt64(sal_Unicode * str, sal_Int64 l, sal_Int16 radix )
+{
+#ifndef SAL_INT64_IS_STRUCT
+ sal_Unicode buf[RTL_USTR_MAX_VALUEOFINT64];
+ sal_Int32 charPos = RTL_USTR_MAX_VALUEOFINT64 - 1;
+ sal_Bool negative = (l < 0);
+
+ if (radix < RTL_USTR_MIN_RADIX || radix > RTL_USTR_MAX_RADIX)
+ radix = 10;
+
+ if (!negative) {
+ l = -l;
+ }
+
+ while (l <= -radix) {
+ buf[charPos--] = RTL_STR_DIGITS[(sal_Int32)(-(l % radix))];
+ l = l / radix;
+ }
+ buf[charPos] = RTL_STR_DIGITS[(sal_Int32)(-l)];
+
+ if (negative) {
+ buf[--charPos] = '-';
+ }
+
+ rtl_copyMemory(str, buf + charPos, (RTL_USTR_MAX_VALUEOFINT64 - charPos) * sizeof(sal_Unicode));
+
+ return (RTL_USTR_MAX_VALUEOFINT64 - charPos);
+#else
+ return 0;
+#endif
+}
+
+/*************************************************************************
+ * numberToStringImpl
+ */
+
+#define FLOAT_MAX_POS ( 3.402823e+38)
+#define FLOAT_MAX_NEG (-3.402823e+38)
+#define FLOAT_MIN_POS ( 1.175494351e-38)
+#define FLOAT_MIN_NEG (-1.175494351e-38)
+
+
+sal_Int32 SAL_CALL numberToStringImpl(sal_Unicode * str, double d, sal_Int16 significantDigits )
+{
+ /* Make it very simple without any formatting,
+ * (similar to Double.toString() in Java) */
+ sal_Unicode buf[ RTL_USTR_MAX_VALUEOFDOUBLE ];
+ sal_Unicode* charPos = buf;
+ sal_Int16 i, len, dig, dotPos;
+ sal_Int16 lastNonZeroPos;
+ sal_Int16 nExpDigits;
+ sal_Bool bExp;
+ double dExp;
+
+ if( d == 0 )
+ {
+ *(charPos++) = L'0';
+ *(charPos++) = L'.';
+ *(charPos++) = L'0';
+ }
+ else
+ {
+ if( d < 0 )
+ {
+ *(charPos++) = L'-';
+ d = -d;
+ }
+
+ dExp = log10( d );
+ bExp = sal_False;
+ if( dExp > 7 || dExp <= -7 )
+ bExp = sal_True;
+
+ dExp = floor( dExp );
+ d /= pow( 10, dExp );
+ while( d > 10 )
+ {
+ d /= 10.0;
+ dExp += 1.0;
+ }
+
+ if( d < 1.0 )
+ significantDigits++;
+
+ dotPos = bExp ? 0 : (sal_Int16)dExp;
+ lastNonZeroPos = 0;
+ for( i = 0 ; i < significantDigits ; i++ )
+ {
+ dig = (sal_Int16)d;
+ if( dig )
+ lastNonZeroPos = i;
+ *(charPos++) = L'0' + dig;
+ if( i == dotPos )
+ *(charPos++) = L'.';
+ d -= (double)dig;
+ d *= 10.0;
+ }
+
+ /* Kill trailing zeros */
+ if( lastNonZeroPos > dotPos + 1 )
+ charPos -= (significantDigits - 1 - lastNonZeroPos);
+
+ /* exponent */
+ if( bExp )
+ {
+ *(charPos++) = L'E';
+ if( dExp < 0.0 )
+ {
+ dExp = -dExp;
+ *(charPos++) = L'-';
+ }
+
+ nExpDigits = 1;
+ while( dExp >= 10.0 )
+ {
+ nExpDigits++;
+ dExp /= 10;
+ }
+ for( i = 0 ; i < nExpDigits ; i++ )
+ {
+ dig = (sal_Int16)dExp;
+ *(charPos++) = L'0' + dig;
+ dExp -= (double)dig;
+ dExp *= 10.0;
+ }
+ }
+ }
+
+ *(charPos++) = 0;
+ len = charPos - buf;
+ rtl_copyMemory( str, buf, len * sizeof(sal_Unicode) );
+ return len - 1;
+}
+
+/*************************************************************************/
+
+sal_Int32 SAL_CALL getInfinityStr(sal_Unicode * This, sal_Bool bNeg)
+{
+ sal_Char InfinityStr[] = "-Infinity";
+ sal_Char* pStr = bNeg ? InfinityStr : InfinityStr + 1;
+ sal_Int32 len = bNeg ? 9 : 8;
+ sal_Int32 i;
+ for ( i = 0; i < len+1; i++ )
+ *(This+i) = *(pStr+i);
+ return len;
+}
+
+sal_Int32 SAL_CALL getNaNStr(sal_Unicode * This)
+{
+ sal_Char NaNStr[] = "NaN";
+ sal_Int32 len = 3;
+ sal_Int32 i;
+ for ( i = 0; i < len+1; i++ )
+ *(This+i) = NaNStr[i];
+ return len;
+}
+
+/*************************************************************************
+ * rtl_ustr_valueOfFloat
+ */
+#define singleSignMask ((sal_uInt32)0x80000000)
+#define singleExpMask ((sal_uInt32)0x7f800000)
+#define singleFractMask (~(singleSignMask|singleExpMask))
+#define singleExpShift ((sal_uInt32)23)
+
+sal_Int32 SAL_CALL rtl_ustr_valueOfFloat(sal_Unicode * This, float f)
+{
+ /* Discover obvious special cases of NaN and Infinity
+ * (like in Java Ctor FloatingDecimal( float f ) ) */
+ sal_uInt32 fBits = *(sal_uInt32*)(&f);
+ sal_uInt32 binExp = (sal_uInt32)( (fBits & singleExpMask) >> singleExpShift );
+ sal_uInt32 fractBits = fBits & singleFractMask;
+ if ( binExp == (sal_uInt32)(singleExpMask>>singleExpShift) )
+ {
+ if ( fractBits == 0L )
+ return getInfinityStr(This, (sal_Bool)(f < 0.0));
+ else
+ return getNaNStr(This);
+ }
+ return numberToStringImpl( This, (double)f, 8 );
+}
+
+/*************************************************************************
+ * rtl_ustr_valueOfDouble
+ */
+#ifndef WNT
+#define signMask ((sal_uInt64)0x8000000000000000LL)
+#define expMask ((sal_uInt64)0x7ff0000000000000LL)
+#else
+#define signMask ((sal_uInt64)0x8000000000000000L)
+#define expMask ((sal_uInt64)0x7ff0000000000000L)
+#endif
+
+#define fractMask (~(signMask|expMask))
+#define expShift ((sal_uInt32)52)
+
+sal_Int32 SAL_CALL rtl_ustr_valueOfDouble(sal_Unicode * This, double d)
+{
+#ifndef SAL_INT64_IS_STRUCT
+ /* Discover obvious special cases of NaN and Infinity.
+ * (like in Java Ctor FloatingDecimal( double d ) ) */
+ sal_uInt64 dBits = *(sal_uInt64*)(&d);
+ sal_uInt32 binExp = (sal_uInt32)( (dBits & expMask) >> expShift );
+ sal_uInt64 fractBits = dBits & fractMask;
+ if ( binExp == (int)(expMask >> expShift) )
+ {
+ if ( fractBits == 0L )
+ return getInfinityStr(This, (sal_Bool)(d < 0.0));
+ else
+ return getNaNStr(This);
+ }
+#endif
+ return numberToStringImpl( This, d, 17 );
+}
+
+/*************************************************************************
+ * rtl_ustr_toInt32
+ */
+sal_Int32 SAL_CALL rtl_ustr_toInt32( sal_Unicode * str, sal_Int16 radix )
+{
+ sal_Char* stopstring;
+ sal_Char* CharStr;
+ sal_Char* pChar;
+ sal_Int32 length, i, nVal;
+ sal_Unicode wc;
+
+ /* simple conversion to 8 bit string */
+ length = rtl_ustr_getLength( str );
+ CharStr = (sal_Char*)rtl_allocateMemory( length + 1 );
+ pChar = CharStr;
+ for( i = 0 ; i < length ; i++ )
+ {
+ wc = *(str++);
+ *(pChar++) = ( wc <= 255 ) ? (sal_Char)wc : 0;
+ }
+ CharStr[ length ] = 0;
+ nVal = strtol( CharStr, &stopstring, radix );
+ rtl_freeMemory( CharStr );
+ return nVal;
+}
+
+/*************************************************************************
+ * Help function for rtl_ustr_toInt64
+ */
+sal_Int16 getDigit( sal_Unicode ch, sal_Int16 radix )
+{
+ sal_Int16 value = -1;
+ if( ch >= L'0' && ch <= L'9' )
+ value = ch - L'0';
+ else if( ch >= L'a' && ch <= L'z' )
+ value = ch - L'a' + 10;
+ else if( ch >= L'A' && ch <= L'Z' )
+ value = ch - L'A' + 10;
+ return ( value < radix ) ? value : -1;
+}
+
+#ifndef WNT
+#define INT64_MIN_VALUE 0x8000000000000000LL;
+#define INT64_MAX_VALUE 0x7fffffffffffffffLL;
+#else
+#define INT64_MIN_VALUE 0x8000000000000000L;
+#define INT64_MAX_VALUE 0x7fffffffffffffffL;
+#endif
+
+/*************************************************************************
+ * rtl_ustr_toInt64 (like in Java)
+ */
+sal_Int64 SAL_CALL rtl_ustr_toInt64( sal_Unicode * str, sal_Int16 radix )
+{
+#ifndef SAL_INT64_IS_STRUCT
+ sal_Int64 result = 0;
+ sal_Bool negative = sal_False;
+ sal_Int32 i = 0;
+ sal_Int32 max = rtl_ustr_getLength( str );
+ sal_Int64 limit;
+ sal_Int64 multmin;
+ sal_Int32 digit;
+
+ if( max == 0 )
+ return 0;
+
+ if( radix < RTL_USTR_MIN_RADIX || radix > RTL_USTR_MAX_RADIX )
+ radix = 10;
+
+ while( i < max && (str[i] == L' ' || str[i] == L'\t') )
+ i++;
+
+ if( str[i] == L'-' )
+ {
+ negative = sal_True;
+ limit = INT64_MIN_VALUE;
+ i++;
+ }
+ else
+ {
+ limit = -INT64_MAX_VALUE;
+ }
+ multmin = limit / radix;
+ if( i < max )
+ {
+ digit = getDigit( str[i++], radix );
+ if( digit < 0 )
+ return 0;
+ result = -digit;
+ }
+ while( i < max )
+ {
+ // Accumulating negatively avoids surprises near MAX_VALUE
+ digit = getDigit( str[i++], radix );
+ if( digit < 0 )
+ break;
+
+ if( result < multmin )
+ break;
+
+ result *= radix;
+ if( result < limit + digit )
+ break;
+
+ result -= digit;
+ }
+ if( negative )
+ return result;
+ else
+ return -result;
+
+#endif
+ return 0;
+}
+
+/*************************************************************************
+ * rtl_ustr_toFloat
+ */
+float SAL_CALL rtl_ustr_toFloat( sal_Unicode * str )
+{
+ sal_Char* stopstring;
+ sal_Char* CharStr;
+ sal_Char* pChar;
+ sal_Int32 length, i;
+ sal_Unicode wc;
+ double dVal;
+
+ /* simple conversion to 8 bit string */
+ length = rtl_ustr_getLength( str );
+ CharStr = (sal_Char*)rtl_allocateMemory( length + 1);
+ pChar = CharStr;
+ for( i = 0 ; i < length ; i++ )
+ {
+ wc = *(str++);
+ *(pChar++) = ( wc <= 255 ) ? (sal_Char)wc : 0;
+ }
+ CharStr[ length ] = 0;
+ dVal = strtod( CharStr, &stopstring );
+
+ /* float range? */
+ if( dVal > FLOAT_MAX_POS ||
+ dVal < FLOAT_MAX_NEG ||
+ ( dVal > 0 && dVal < FLOAT_MIN_POS ) ||
+ ( dVal < 0 && dVal > FLOAT_MIN_NEG ) )
+ {
+ dVal = 0.0;
+ }
+ rtl_freeMemory( CharStr );
+ return (float)dVal;
+}
+
+/*************************************************************************
+ * rtl_ustr_toDouble
+ */
+double SAL_CALL rtl_ustr_toDouble( sal_Unicode * str )
+{
+ sal_Char* stopstring;
+ sal_Char* CharStr;
+ sal_Char* pChar;
+ sal_Int32 length, i;
+ sal_Unicode wc;
+ double dVal;
+
+ /* simple conversion to 8 bit string */
+ length = rtl_ustr_getLength( str );
+ CharStr = (sal_Char*)rtl_allocateMemory( length + 1 );
+ pChar = CharStr;
+ for( i = 0 ; i < length ; i++ )
+ {
+ wc = *(str++);
+ *(pChar++) = ( wc <= 255 ) ? (sal_Char)wc : 0;
+ }
+ CharStr[ length ] = 0;
+ dVal = strtod( CharStr, &stopstring );
+ rtl_freeMemory( CharStr );
+ return dVal;
+}
+
+
+/*************************************************************************
+ *
+ * rtl_uString_XXX Functions
+ *
+/*************************************************************************
+
+/*************************************************************************
+ * rtl_uString_acquire
+ */
+void SAL_CALL rtl_uString_acquire( rtl_uString * value )
+{
+ osl_incrementInterlockedCount(&value->refCount);
+}
+
+/*************************************************************************
+ * rtl_uString_release
+ */
+void SAL_CALL rtl_uString_release( rtl_uString * value )
+{
+ if( 0 == osl_decrementInterlockedCount(&value->refCount) )
+ {
+ OSL_ENSHURE( value != &aEmpty_rtl_wString, "static empty string: refCount==0");
+ rtl_freeMemory(value);
+ }
+}
+
+/*************************************************************************
+ * rtl_uString_new
+ */
+void SAL_CALL rtl_uString_new( rtl_uString ** newStr )
+{
+ if (*newStr)
+ rtl_uString_release(*newStr);
+
+ *newStr = &aEmpty_rtl_wString;
+ rtl_uString_acquire( *newStr );
+}
+
+/*************************************************************************
+ * rtl_uString_new_WithLength
+ */
+void SAL_CALL rtl_uString_new_WithLength( rtl_uString ** newStr, sal_Int32 nLen )
+{
+ if (*newStr)
+ rtl_uString_release(*newStr);
+
+ *newStr = (rtl_uString*)rtl_allocateMemory( sizeof(rtl_uString) + (nLen * sizeof(sal_Unicode)) );
+
+ if (!(*newStr)) return;
+
+ (*newStr)->refCount = 1;
+ (*newStr)->length = 0;
+ *((*newStr)->buffer + nLen) = L'\0';
+
+ rtl_zeroMemory((*newStr)->buffer, nLen * sizeof(sal_Unicode));
+}
+
+/*************************************************************************
+ * rtl_uString_newFromString
+ */
+void SAL_CALL rtl_uString_newFromString( rtl_uString ** newStr, rtl_uString * value )
+{
+ rtl_uString * pOrg;
+
+ if (value->length == 0)
+ {
+ rtl_uString_new(newStr);
+ return;
+ }
+
+ pOrg = *newStr;
+ *newStr = (rtl_uString*)rtl_allocateMemory( sizeof(rtl_uString) + (value->length * sizeof(sal_Unicode)) );
+ if ( *newStr )
+ {
+ (*newStr)->refCount = 1;
+ (*newStr)->length = value->length;
+ rtl_copyMemory((*newStr)->buffer, value->buffer, (value->length+1) * sizeof(sal_Unicode));
+ }
+
+ /* must be done at least, if left == *newStr */
+ if ( pOrg )
+ rtl_uString_release( pOrg );
+}
+
+/*************************************************************************
+ * rtl_uString_newFromStr
+ */
+void SAL_CALL rtl_uString_newFromStr( rtl_uString ** newStr, const sal_Unicode * value )
+{
+ rtl_uString * pOrg;
+ sal_Int32 length;
+
+ if (!value)
+ {
+ rtl_uString_new(newStr);
+ return;
+ }
+
+ length = rtl_ustr_getLength(value);
+
+ pOrg = *newStr;
+ *newStr = (rtl_uString*)rtl_allocateMemory( sizeof(rtl_uString) + (length * sizeof(sal_Unicode)) );
+ if ( *newStr )
+ {
+ (*newStr)->refCount = 1;
+ (*newStr)->length = length;
+ rtl_copyMemory((*newStr)->buffer, value, (length+1) * sizeof(sal_Unicode));
+ }
+
+ /* must be done at least, if left == *newStr */
+ if ( pOrg )
+ rtl_uString_release( pOrg );
+}
+
+/*************************************************************************
+ * rtl_uString_newFromStr_WithLength
+ */
+void SAL_CALL rtl_uString_newFromStr_WithLength( rtl_uString ** newStr,
+ const sal_Unicode * value,
+ sal_Int32 len)
+{
+ rtl_uString * pOrg;
+
+ if (!value || len < 0 )
+ {
+ rtl_uString_new(newStr);
+ return;
+ }
+
+ pOrg = *newStr;
+ *newStr = (rtl_uString*)rtl_allocateMemory( sizeof(rtl_uString) + (len * sizeof(sal_Unicode)) );
+ if ( *newStr )
+ {
+ (*newStr)->refCount = 1;
+ (*newStr)->length = len;
+ rtl_copyMemory((*newStr)->buffer, value, len * sizeof(sal_Unicode));
+ (*newStr)->buffer[len] = 0;
+ }
+
+ /* must be done at least, if left == *newStr */
+ if ( pOrg )
+ rtl_uString_release( pOrg );
+}
+
+/*************************************************************************
+ * rtl_wstr_getLength
+ */
+static sal_Int32 SAL_CALL rtl_wstr_getLength( const wchar_t* str )
+{
+ const wchar_t * pTempStr = str;
+ while( *pTempStr ) pTempStr++;
+ return pTempStr - str;
+}
+
+/*************************************************************************
+ * rtl_uString_newFromWStr
+ */
+void SAL_CALL rtl_uString_newFromWStr( rtl_uString ** newStr, const wchar_t * value )
+{
+ sal_Int32 length;
+ sal_Unicode* p;
+
+ if (!value)
+ {
+ rtl_uString_new(newStr);
+ return;
+ }
+
+ length = rtl_wstr_getLength(value);
+
+ if (*newStr)
+ rtl_uString_release(*newStr);
+
+ *newStr = (rtl_uString*)rtl_allocateMemory( sizeof(rtl_uString) + (length * sizeof(sal_Unicode)) );
+ if ( *newStr )
+ {
+ (*newStr)->refCount = 1;
+ (*newStr)->length = length;
+
+ p = (*newStr)->buffer;
+ while ( length )
+ {
+ *p = (sal_Unicode)(*value);
+ p++;
+ value++;
+ length--;
+ }
+ *p = 0;
+ }
+}
+
+/*************************************************************************
+ * rtl_uString_newFromWStr_WithLength
+ */
+void SAL_CALL rtl_uString_newFromWStr_WithLength( rtl_uString ** newStr,
+ const wchar_t * value,
+ sal_Int32 len)
+{
+ sal_Unicode* p;
+
+ if (!value || len < 0)
+ {
+ rtl_uString_new(newStr);
+ return;
+ }
+
+ if (*newStr)
+ rtl_uString_release(*newStr);
+
+ *newStr = (rtl_uString*)rtl_allocateMemory( sizeof(rtl_uString) + (len * sizeof(sal_Unicode)) );
+ if ( *newStr )
+ {
+ (*newStr)->refCount = 1;
+ (*newStr)->length = len;
+
+ p = (*newStr)->buffer;
+ while ( len )
+ {
+ *p = (sal_Unicode)(*value);
+ p++;
+ value++;
+ len--;
+ }
+ *p = 0;
+ }
+}
+
+/*************************************************************************
+ * rtl_uString_newFromASCII
+ */
+void SAL_CALL rtl_uString_newFromAscii( rtl_uString ** newStr, const sal_Char * value )
+{
+ sal_Int32 length;
+ sal_Unicode* p;
+
+ if (!value)
+ {
+ rtl_uString_new(newStr);
+ return;
+ }
+
+ length = rtl_str_getLength( value );
+
+ if (*newStr)
+ rtl_uString_release(*newStr);
+
+ *newStr = (rtl_uString*)rtl_allocateMemory( sizeof(rtl_uString) + (length * sizeof(sal_Unicode)) );
+ if ( *newStr )
+ {
+ (*newStr)->refCount = 1;
+ (*newStr)->length = length;
+
+ p = (*newStr)->buffer;
+ while ( length )
+ {
+ /* Check ASCII range */
+ OSL_ENSHURE( (*value & 0x80) == 0, "Found ASCII char > 127");
+
+ *p = (sal_Unicode)(*value);
+ p++;
+ value++;
+ length--;
+ }
+ *p = 0;
+ }
+}
+
+/*************************************************************************
+ * rtl_uString_assign
+ */
+void SAL_CALL rtl_uString_assign( /*inout*/rtl_uString ** str, rtl_uString * rightValue )
+{
+ rtl_uString_acquire(rightValue);
+
+ if (*str)
+ rtl_uString_release(*str);
+
+ *str = rightValue;
+}
+
+/*************************************************************************
+ * rtl_uString_getLength
+ */
+sal_Int32 SAL_CALL rtl_uString_getLength( rtl_uString * str )
+{
+ return str->length;
+}
+
+/*************************************************************************
+ * rtl_uString_getStr
+ */
+sal_Unicode * SAL_CALL rtl_uString_getStr( rtl_uString * str )
+{
+ return str->buffer;
+}
+
+/*************************************************************************
+ * rtl_uString_newConcat
+ */
+void SAL_CALL rtl_uString_newConcat( rtl_uString ** newStr, rtl_uString * left, rtl_uString * right )
+{
+ rtl_uString * pOrg = *newStr;
+ if( !right->length )
+ {
+ *newStr = left;
+ rtl_uString_acquire( left );
+ }
+ else if( !left->length )
+ {
+ *newStr = right;
+ rtl_uString_acquire( right );
+ }
+ else
+ {
+ rtl_uString *tmpStr = NULL;
+ sal_Int32 nNewLen = left->length + right->length;
+ rtl_uString_new_WithLength(&tmpStr, nNewLen);
+ tmpStr->length = nNewLen;
+
+ rtl_copyMemory( tmpStr->buffer, left->buffer, left->length * sizeof(sal_Unicode));
+ rtl_copyMemory( tmpStr->buffer + left->length, right->buffer, right->length * sizeof(sal_Unicode));
+ tmpStr->buffer[nNewLen] = 0;
+ *newStr = tmpStr;
+ }
+ /* must be done at least, if left == *newStr */
+ if( pOrg )
+ rtl_uString_release(pOrg);
+}
+
+/*************************************************************************
+ * rtl_uString_newReplace
+ */
+void SAL_CALL rtl_uString_newReplace( rtl_uString ** newStr,
+ rtl_uString * str,
+ sal_Unicode oldChar,
+ sal_Unicode newChar)
+{
+ rtl_uString_newFromString(newStr, str);
+
+ if (!(*newStr)) return;
+
+ rtl_ustr_replaceChar_WithLength((*newStr)->buffer, (*newStr)->length, oldChar, newChar);
+}
+
+/*************************************************************************
+ * rtl_uString_newReplaceStrAt
+ */
+void SAL_CALL rtl_uString_newReplaceStrAt( rtl_uString ** newStr,
+ rtl_uString * str,
+ sal_Int32 index,
+ sal_Int32 count,
+ rtl_uString * newSub)
+{
+ sal_Unicode *pBuffer = NULL;
+ sal_Int32 size = sizeof(sal_Unicode);
+
+ if (count == 0 && newSub->length == 0)
+ {
+ rtl_uString_newFromString(newStr, str);
+ return;
+ }
+
+ if (count == 0)
+ {
+ rtl_uString_new_WithLength(newStr, str->length + newSub->length);
+ if (!(*newStr)) return;
+ pBuffer = (*newStr)->buffer;
+ (*newStr)->length = str->length + newSub->length;
+ rtl_copyMemory(pBuffer, str->buffer, index * size);
+ rtl_copyMemory(pBuffer + index, newSub->buffer, newSub->length * size);
+ rtl_copyMemory(pBuffer + index + newSub->length, str->buffer + index,
+ (str->length - index) * size);
+
+ return;
+ }
+
+ if (newSub->length == 0)
+ {
+ rtl_uString_new_WithLength(newStr, str->length - count);
+ if (!(*newStr)) return;
+ pBuffer = (*newStr)->buffer;
+ (*newStr)->length = str->length - count;
+ rtl_copyMemory(pBuffer, str->buffer, index * size);
+ rtl_copyMemory(pBuffer + index, str->buffer + index + count,
+ (str->length - index - count) * size);
+
+ return;
+ }
+
+ rtl_uString_new_WithLength(newStr, str->length - count + newSub->length);
+ if (!(*newStr)) return;
+ pBuffer = (*newStr)->buffer;
+ (*newStr)->length = str->length - count + newSub->length;
+ rtl_copyMemory(pBuffer, str->buffer, index * size);
+ rtl_copyMemory(pBuffer + index, newSub->buffer, newSub->length * size);
+ rtl_copyMemory(pBuffer + index + newSub->length, str->buffer + index + count,
+ (str->length - index - count) * size);
+
+ return;
+}
+
+/*************************************************************************
+ * rtl_uString_newToLowerCase
+ */
+void SAL_CALL rtl_uString_newToLowerCase( rtl_uString ** newStr,
+ rtl_uString * str,
+ struct _rtl_Locale * locale )
+{
+ if (locale && locale->Language->length == 2
+ && locale->Language->buffer[0] == 't'
+ && locale->Language->buffer[0] == 'r' )
+ {
+ sal_Int32 i;
+ sal_Int32 len = str->length;
+
+ rtl_uString_new_WithLength(newStr, str->length);
+
+ if (!(*newStr)) return;
+
+ (*newStr)->length = str->length;
+
+ /* special loop for Turkey */
+ for (i = 0; i < len; i++)
+ {
+ sal_Unicode ch = str->buffer[i];
+ if (ch == L'I')
+ {
+ (*newStr)->buffer[i] = (sal_Unicode)0x0131; /* dotless small i */
+ continue;
+ }
+ if ((sal_uInt16)ch == 0x0130) /* dotted I */
+ {
+ (*newStr)->buffer[i] = L'i'; /* dotted i */
+ continue;
+ }
+ (*newStr)->buffer[i] = rtl_char_toLowerCase(ch);
+ }
+ } else
+ {
+ rtl_uString_newFromString(newStr, str);
+
+ if (!(*newStr)) return;
+
+ rtl_ustr_toAsciiLowerCase_WithLength((*newStr)->buffer, (*newStr)->length);
+ }
+}
+
+/*************************************************************************
+ * rtl_uString_newToUpperCase
+ */
+void SAL_CALL rtl_uString_newToUpperCase( rtl_uString ** newStr,
+ rtl_uString * str,
+ struct _rtl_Locale * locale )
+{
+ sal_Int32 i;
+ sal_Int32 len = str->length;
+ sal_Int32 resultOffset = 0;
+ sal_Unicode *result = (sal_Unicode*)rtl_allocateMemory((len + 1)* sizeof(sal_Unicode));
+
+ if (locale && locale->Language->length == 2
+ && locale->Language->buffer[0] == 't'
+ && locale->Language->buffer[0] == 'r' )
+ {
+ /* special loop for Turkey */
+ for (i = 0; i < len; i++)
+ {
+ sal_Unicode ch = str->buffer[i];
+ if ((sal_uInt16)ch == 0x0131) /* dotless i */
+ {
+ result[i+resultOffset] = L'I'; /* cap I */
+ continue;
+ }
+ if (ch == L'i')
+ {
+ result[i+resultOffset] = (sal_Unicode)0x0130; /* dotted cap i */
+ continue;
+ }
+ if ((sal_uInt16)ch == 0x00DF) /* sharp s */
+ {
+ /* Grow result. */
+ sal_Unicode *result2 = (sal_Unicode*)rtl_allocateMemory((len + 1 + resultOffset + 1) * sizeof(sal_Unicode));
+ rtl_copyMemory(result2, result, (i + resultOffset) * sizeof(sal_Unicode));
+ result2[i+resultOffset] = L'S';
+ resultOffset++;
+ result2[i+resultOffset] = L'S';
+ rtl_freeMemory(result);
+ result = result2;
+ continue;
+ }
+ result[i+resultOffset] = rtl_char_toUpperCase(ch);
+ }
+ } else
+ {
+ for (i = 0; i < len; i++)
+ {
+ sal_Unicode ch = str->buffer[i];
+
+ if ((sal_uInt16)ch == 0x00DF) /* sharp s */
+ {
+ /* Grow result. */
+ sal_Unicode *result2 = (sal_Unicode*)rtl_allocateMemory((len + 1 + resultOffset + 1) * sizeof(sal_Unicode));
+ rtl_copyMemory(result2, result, (i + resultOffset) * sizeof(sal_Unicode));
+ result2[i+resultOffset] = L'S';
+ resultOffset++;
+ result2[i+resultOffset] = L'S';
+ rtl_freeMemory(result);
+ result = result2;
+ continue;
+ }
+ result[i+resultOffset] = rtl_char_toUpperCase(ch);
+ }
+
+ }
+
+ result[len + resultOffset] = L'\0';
+ rtl_uString_newFromStr_WithLength(newStr, result, len + resultOffset);
+ rtl_freeMemory(result);
+}
+
+/*************************************************************************
+ * rtl_uString_newTrim
+ */
+void SAL_CALL rtl_uString_newTrim( rtl_uString ** newStr, rtl_uString * str )
+{
+ rtl_uString_newFromString(newStr, str);
+
+ if (!(*newStr)) return;
+
+ (*newStr)->length = rtl_ustr_trim_WithLength((*newStr)->buffer, (*newStr)->length);
+}
+
+/*************************************************************************
+ * rtl_uString_getTokenCount
+ */
+sal_Int32 SAL_CALL rtl_uString_getTokenCount( rtl_uString * str , sal_Unicode cTok)
+{
+ sal_Int32 count = 0;
+ sal_Int32 index1 = 0;
+ sal_Int32 index2 = 0;
+ sal_Unicode * buffer = str->buffer;
+
+ while ((index2 = rtl_ustr_indexOfChar_WithLength(buffer + index1, str->length - index1, cTok)) >= 0)
+ {
+ if (index2 <= (str->length - index1) && index2 >= 0)
+ count++;
+
+ index1 += index2 + 1;
+ }
+
+ if (index2 < 0 && index1 <= str->length)
+ count++;
+
+ return count;
+}
+
+/*************************************************************************
+ * rtl_uString_getToken
+ */
+void SAL_CALL rtl_uString_getToken( rtl_uString ** newStr , rtl_uString * str, sal_Int32 nToken, sal_Unicode cTok)
+{
+ sal_Int32 count = 0;
+ sal_Int32 index1 = 0;
+ sal_Int32 index2 = 0;
+ sal_Unicode * buffer = str->buffer;
+
+ while ((index2 = rtl_ustr_indexOfChar_WithLength(buffer + index1, str->length - index1, cTok)) >= 0)
+ {
+ if (count == nToken)
+ {
+ rtl_uString_newFromStr_WithLength( newStr, buffer + index1, index2 );
+ return;
+ }
+
+ if (index2 <= (str->length - index1) && index2 >= 0)
+ count++;
+
+ index1 += index2 + 1;
+ }
+
+ if (nToken == 0 || nToken == count)
+ rtl_uString_newFromStr_WithLength( newStr, buffer + index1, str->length - index1 );
+ else
+ rtl_uString_new(newStr);
+
+ return;
+}
+
+
+void SAL_CALL rtl_string2UString( rtl_uString** newStr, const sal_Char* pStr, sal_Int32 nLen,
+ rtl_TextEncoding encoding, sal_uInt32 nCvtFlags )
+{
+ if (nLen)
+ {
+ sal_Unicode* pData;
+ rtl_TextEncodingInfo aTextEncInfo;
+ rtl_TextToUnicodeConverter hConverter = rtl_createTextToUnicodeConverter( encoding );
+ sal_uInt32 nInfo;
+ sal_Size nSrcBytes;
+ sal_Size nDestChars;
+ sal_Size nNewLen;
+
+ /* get TextEncodingInfo */
+ aTextEncInfo.StructSize = sizeof( aTextEncInfo );
+ rtl_getTextEncodingInfo( encoding, &aTextEncInfo );
+
+ /* Zuerst konvertieren wir mit der wahrscheinlichen Anzahl */
+ /* der zu konvertierenden Zeichen */
+ nNewLen = nLen; /* (aTextEncInfo.AverageCharSize ? aTextEncInfo.AverageCharSize : 1); */
+
+ pData = (sal_Unicode*)rtl_allocateMemory( (1 + nNewLen) * sizeof(sal_Unicode) );
+ nDestChars = rtl_convertTextToUnicode( hConverter, 0,
+ pStr, nLen,
+ pData, nNewLen,
+ nCvtFlags,
+ &nInfo, &nSrcBytes );
+
+ /* String entsprechend der durch das Konvertieren tatsaechlich */
+ /* entstehenden Bytes anpassen */
+ pData[nDestChars] = L'\0';
+
+ rtl_uString_newFromStr_WithLength(newStr, pData, nDestChars);
+
+ rtl_destroyTextToUnicodeConverter( hConverter );
+ rtl_freeMemory( pData );
+ } else
+ {
+ rtl_uString_new(newStr);
+ }
+}
+
+void SAL_CALL rtl_uString2String( rtl_String** newStr, const sal_Unicode * pWStr, sal_Int32 nWLen,
+ rtl_TextEncoding encoding, sal_uInt32 nCvtFlags )
+{
+ if (nWLen)
+ {
+ sal_Char* pData;
+ rtl_TextEncodingInfo aTextEncInfo;
+ rtl_UnicodeToTextConverter hConverter = rtl_createUnicodeToTextConverter( encoding );
+ sal_Size nSrcChars;
+ sal_Size nDestBytes;
+ sal_Size nNewLen;
+ sal_uInt32 nInfo;
+
+ /* get TextEncodingInfo */
+ aTextEncInfo.StructSize = sizeof( aTextEncInfo );
+ rtl_getTextEncodingInfo( encoding, &aTextEncInfo );
+
+ /* Zuerst konvertieren wir mit der wahrscheinlichen Anzahl */
+ /* der zu konvertierenden Zeichen */
+ nNewLen = nWLen * (aTextEncInfo.AverageCharSize ? aTextEncInfo.AverageCharSize : 1) * 6;
+
+ pData = (sal_Char*)rtl_allocateMemory( nNewLen );
+ nDestBytes = rtl_convertUnicodeToText( hConverter, 0,
+ pWStr, nWLen,
+ pData, nNewLen,
+ nCvtFlags,
+ &nInfo, &nSrcChars );
+ pData[nDestBytes] = '\0';
+
+ rtl_string_newFromStr_WithLength(newStr, pData, nDestBytes);
+
+ rtl_destroyUnicodeToTextConverter( hConverter );
+ rtl_freeMemory( pData );
+ } else
+ {
+ rtl_string_new(newStr);
+ }
+}
+
+