xref: /aoo42x/main/sal/rtl/source/strtmpl.c (revision cdf0e10c)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 /* ======================================================================= */
29 /* Internal C-String help functions which could be used without the        */
30 /* String-Class                                                            */
31 /* ======================================================================= */
32 
33 /*
34 inline void rtl_str_ImplCopy( IMPL_RTL_STRCODE* pDest,
35                               const IMPL_RTL_STRCODE* pSrc,
36                               sal_Int32 nCount )
37 {
38     while ( nCount > 0 )
39     {
40         *pDest = *pSrc;
41         pDest++;
42         pSrc++;
43         nCount--;
44     }
45 }
46 */
47 
48 #define rtl_str_ImplCopy( _pDest, _pSrc, _nCount )                  \
49 {                                                                   \
50     IMPL_RTL_STRCODE*       __mm_pDest      = _pDest;               \
51     const IMPL_RTL_STRCODE* __mm_pSrc       = _pSrc;                \
52     sal_Int32               __mm_nCount     = _nCount;              \
53     while ( __mm_nCount > 0 )                                       \
54     {                                                               \
55         *__mm_pDest = *__mm_pSrc;                                   \
56         __mm_pDest++;                                               \
57         __mm_pSrc++;                                                \
58         __mm_nCount--;                                              \
59     }                                                               \
60 }
61 
62 /* ======================================================================= */
63 /* C-String functions which could be used without the String-Class         */
64 /* ======================================================================= */
65 
66 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( getLength )( const IMPL_RTL_STRCODE* pStr )
67 {
68     const IMPL_RTL_STRCODE* pTempStr = pStr;
69     while( *pTempStr )
70         pTempStr++;
71     return pTempStr-pStr;
72 }
73 
74 /* ----------------------------------------------------------------------- */
75 
76 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( compare )( const IMPL_RTL_STRCODE* pStr1,
77                                                 const IMPL_RTL_STRCODE* pStr2 )
78 {
79     sal_Int32 nRet;
80     while ( ((nRet = ((sal_Int32)(IMPL_RTL_USTRCODE(*pStr1)))-
81                      ((sal_Int32)(IMPL_RTL_USTRCODE(*pStr2)))) == 0) &&
82             *pStr2 )
83     {
84         pStr1++;
85         pStr2++;
86     }
87 
88     return nRet;
89 }
90 
91 /* ----------------------------------------------------------------------- */
92 
93 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( compare_WithLength )( const IMPL_RTL_STRCODE* pStr1,
94                                                            sal_Int32 nStr1Len,
95                                                            const IMPL_RTL_STRCODE* pStr2,
96                                                            sal_Int32 nStr2Len )
97 {
98     sal_Int32 nRet = nStr1Len - nStr2Len;
99     int nCount = (nRet <= 0) ? nStr1Len : nStr2Len;
100 
101     --pStr1;
102     --pStr2;
103     while( (--nCount >= 0) && (*++pStr1 == *++pStr2) );
104 
105     if( nCount >= 0 )
106         nRet = ((sal_Int32)(IMPL_RTL_USTRCODE( *pStr1 )))
107              - ((sal_Int32)(IMPL_RTL_USTRCODE( *pStr2 )));
108 
109     return nRet;
110 }
111 
112 /* ----------------------------------------------------------------------- */
113 
114 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( shortenedCompare_WithLength )( const IMPL_RTL_STRCODE* pStr1,
115                                                                     sal_Int32 nStr1Len,
116                                                                     const IMPL_RTL_STRCODE* pStr2,
117                                                                     sal_Int32 nStr2Len,
118                                                                     sal_Int32 nShortenedLength )
119 {
120     const IMPL_RTL_STRCODE* pStr1End = pStr1 + nStr1Len;
121     const IMPL_RTL_STRCODE* pStr2End = pStr2 + nStr2Len;
122     sal_Int32               nRet;
123     while ( (nShortenedLength > 0) &&
124             (pStr1 < pStr1End) && (pStr2 < pStr2End) )
125     {
126         nRet = ((sal_Int32)(IMPL_RTL_USTRCODE( *pStr1 )))-
127                ((sal_Int32)(IMPL_RTL_USTRCODE( *pStr2 )));
128         if ( nRet )
129             return nRet;
130 
131         nShortenedLength--;
132         pStr1++;
133         pStr2++;
134     }
135 
136     if ( nShortenedLength <= 0 )
137         return 0;
138     return nStr1Len - nStr2Len;
139 }
140 
141 /* ----------------------------------------------------------------------- */
142 
143 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( reverseCompare_WithLength )( const IMPL_RTL_STRCODE* pStr1,
144                                                                   sal_Int32 nStr1Len,
145                                                                   const IMPL_RTL_STRCODE* pStr2,
146                                                                   sal_Int32 nStr2Len )
147 {
148     const IMPL_RTL_STRCODE* pStr1Run = pStr1+nStr1Len;
149     const IMPL_RTL_STRCODE* pStr2Run = pStr2+nStr2Len;
150     sal_Int32               nRet;
151     while ( (pStr1 < pStr1Run) && (pStr2 < pStr2Run) )
152     {
153         pStr1Run--;
154         pStr2Run--;
155         nRet = ((sal_Int32)(IMPL_RTL_USTRCODE( *pStr1Run )))-
156                ((sal_Int32)(IMPL_RTL_USTRCODE( *pStr2Run )));
157         if ( nRet )
158             return nRet;
159     }
160 
161     return nStr1Len - nStr2Len;
162 }
163 
164 /* ----------------------------------------------------------------------- */
165 
166 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( compareIgnoreAsciiCase )( const IMPL_RTL_STRCODE* pStr1,
167                                                                const IMPL_RTL_STRCODE* pStr2 )
168 {
169     sal_Int32   nRet;
170     sal_Int32   c1;
171     sal_Int32   c2;
172     do
173     {
174         /* If character between 'A' and 'Z', than convert it to lowercase */
175         c1 = (sal_Int32)IMPL_RTL_USTRCODE( *pStr1 );
176         c2 = (sal_Int32)IMPL_RTL_USTRCODE( *pStr2 );
177         if ( (c1 >= 65) && (c1 <= 90) )
178             c1 += 32;
179         if ( (c2 >= 65) && (c2 <= 90) )
180             c2 += 32;
181         nRet = c1-c2;
182         if ( nRet != 0 )
183             return nRet;
184 
185         pStr1++;
186         pStr2++;
187     }
188     while ( c2 );
189 
190     return 0;
191 }
192 
193 /* ----------------------------------------------------------------------- */
194 
195 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( compareIgnoreAsciiCase_WithLength )( const IMPL_RTL_STRCODE* pStr1,
196                                                                           sal_Int32 nStr1Len,
197                                                                           const IMPL_RTL_STRCODE* pStr2,
198                                                                           sal_Int32 nStr2Len )
199 {
200     const IMPL_RTL_STRCODE* pStr1End = pStr1 + nStr1Len;
201     const IMPL_RTL_STRCODE* pStr2End = pStr2 + nStr2Len;
202     sal_Int32   nRet;
203     sal_Int32   c1;
204     sal_Int32   c2;
205     while ( (pStr1 < pStr1End) && (pStr2 < pStr2End) )
206     {
207         /* If character between 'A' and 'Z', than convert it to lowercase */
208         c1 = (sal_Int32)IMPL_RTL_USTRCODE( *pStr1 );
209         c2 = (sal_Int32)IMPL_RTL_USTRCODE( *pStr2 );
210         if ( (c1 >= 65) && (c1 <= 90) )
211             c1 += 32;
212         if ( (c2 >= 65) && (c2 <= 90) )
213             c2 += 32;
214         nRet = c1-c2;
215         if ( nRet != 0 )
216             return nRet;
217 
218         pStr1++;
219         pStr2++;
220     }
221 
222     return nStr1Len - nStr2Len;
223 }
224 
225 /* ----------------------------------------------------------------------- */
226 
227 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( shortenedCompareIgnoreAsciiCase_WithLength )( const IMPL_RTL_STRCODE* pStr1,
228                                                                                    sal_Int32 nStr1Len,
229                                                                                    const IMPL_RTL_STRCODE* pStr2,
230                                                                                    sal_Int32 nStr2Len,
231                                                                                    sal_Int32 nShortenedLength )
232 {
233     const IMPL_RTL_STRCODE* pStr1End = pStr1 + nStr1Len;
234     const IMPL_RTL_STRCODE* pStr2End = pStr2 + nStr2Len;
235     sal_Int32               nRet;
236     sal_Int32               c1;
237     sal_Int32               c2;
238     while ( (nShortenedLength > 0) &&
239             (pStr1 < pStr1End) && (pStr2 < pStr2End) )
240     {
241         /* If character between 'A' and 'Z', than convert it to lowercase */
242         c1 = (sal_Int32)IMPL_RTL_USTRCODE( *pStr1 );
243         c2 = (sal_Int32)IMPL_RTL_USTRCODE( *pStr2 );
244         if ( (c1 >= 65) && (c1 <= 90) )
245             c1 += 32;
246         if ( (c2 >= 65) && (c2 <= 90) )
247             c2 += 32;
248         nRet = c1-c2;
249         if ( nRet != 0 )
250             return nRet;
251 
252         nShortenedLength--;
253         pStr1++;
254         pStr2++;
255     }
256 
257     if ( nShortenedLength <= 0 )
258         return 0;
259     return nStr1Len - nStr2Len;
260 }
261 
262 /* ----------------------------------------------------------------------- */
263 
264 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( hashCode )( const IMPL_RTL_STRCODE* pStr )
265 {
266     return IMPL_RTL_STRNAME( hashCode_WithLength )( pStr, IMPL_RTL_STRNAME( getLength )( pStr ) );
267 }
268 
269 /* ----------------------------------------------------------------------- */
270 
271 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( hashCode_WithLength )( const IMPL_RTL_STRCODE* pStr,
272                                                             sal_Int32 nLen )
273 {
274     sal_Int32 h = nLen;
275 
276     if ( nLen < 256 )
277     {
278         while ( nLen > 0 )
279         {
280             h = (h*37) + IMPL_RTL_USTRCODE( *pStr );
281             pStr++;
282             nLen--;
283         }
284     }
285     else
286     {
287         sal_Int32               nSkip;
288         const IMPL_RTL_STRCODE* pEndStr = pStr+nLen-5;
289 
290         /* only sample some characters */
291         /* the first 3, some characters between, and the last 5 */
292         h = (h*39) + IMPL_RTL_USTRCODE( *pStr );
293         pStr++;
294         h = (h*39) + IMPL_RTL_USTRCODE( *pStr );
295         pStr++;
296         h = (h*39) + IMPL_RTL_USTRCODE( *pStr );
297         pStr++;
298 
299         if ( nLen < 32 )
300             nSkip = nLen / 4;
301         else
302             nSkip = nLen / 8;
303         nLen -= 8;
304         while ( nLen > 0 )
305         {
306             h = (h*39) + IMPL_RTL_USTRCODE( *pStr );
307             pStr += nSkip;
308             nLen -= nSkip;
309         }
310 
311         h = (h*39) + IMPL_RTL_USTRCODE( *pEndStr );
312         pEndStr++;
313         h = (h*39) + IMPL_RTL_USTRCODE( *pEndStr );
314         pEndStr++;
315         h = (h*39) + IMPL_RTL_USTRCODE( *pEndStr );
316         pEndStr++;
317         h = (h*39) + IMPL_RTL_USTRCODE( *pEndStr );
318         pEndStr++;
319         h = (h*39) + IMPL_RTL_USTRCODE( *pEndStr );
320     }
321 
322     return h;
323 }
324 
325 /* ----------------------------------------------------------------------- */
326 
327 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( indexOfChar )( const IMPL_RTL_STRCODE* pStr,
328                                                     IMPL_RTL_STRCODE c )
329 {
330     const IMPL_RTL_STRCODE* pTempStr = pStr;
331     while ( *pTempStr )
332     {
333         if ( *pTempStr == c )
334             return pTempStr-pStr;
335 
336         pTempStr++;
337     }
338 
339     return -1;
340 }
341 
342 /* ----------------------------------------------------------------------- */
343 
344 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( indexOfChar_WithLength )( const IMPL_RTL_STRCODE* pStr,
345                                                                sal_Int32 nLen,
346                                                                IMPL_RTL_STRCODE c )
347 {
348     const IMPL_RTL_STRCODE* pTempStr = pStr;
349     while ( nLen > 0 )
350     {
351         if ( *pTempStr == c )
352             return pTempStr-pStr;
353 
354         pTempStr++;
355         nLen--;
356     }
357 
358     return -1;
359 }
360 
361 /* ----------------------------------------------------------------------- */
362 
363 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( lastIndexOfChar )( const IMPL_RTL_STRCODE* pStr,
364                                                         IMPL_RTL_STRCODE c )
365 {
366     return IMPL_RTL_STRNAME( lastIndexOfChar_WithLength )( pStr, IMPL_RTL_STRNAME( getLength )( pStr ), c );
367 }
368 
369 /* ----------------------------------------------------------------------- */
370 
371 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( lastIndexOfChar_WithLength )( const IMPL_RTL_STRCODE* pStr,
372                                                                    sal_Int32 nLen,
373                                                                    IMPL_RTL_STRCODE c )
374 {
375     pStr += nLen;
376     while ( nLen > 0 )
377     {
378         nLen--;
379         pStr--;
380 
381         if ( *pStr == c )
382             return nLen;
383     }
384 
385     return -1;
386 }
387 
388 /* ----------------------------------------------------------------------- */
389 
390 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( indexOfStr )( const IMPL_RTL_STRCODE* pStr,
391                                                    const IMPL_RTL_STRCODE* pSubStr )
392 {
393     return IMPL_RTL_STRNAME( indexOfStr_WithLength )( pStr, IMPL_RTL_STRNAME( getLength )( pStr ),
394                                                       pSubStr, IMPL_RTL_STRNAME( getLength )( pSubStr ) );
395 }
396 
397 /* ----------------------------------------------------------------------- */
398 
399 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( indexOfStr_WithLength )( const IMPL_RTL_STRCODE* pStr,
400                                                               sal_Int32 nStrLen,
401                                                               const  IMPL_RTL_STRCODE* pSubStr,
402                                                               sal_Int32 nSubLen )
403 {
404     /* faster search for a single character */
405     if ( nSubLen < 2 )
406     {
407         /* an empty SubString is always not foundable */
408         if ( nSubLen == 1 )
409         {
410             IMPL_RTL_STRCODE        c = *pSubStr;
411             const IMPL_RTL_STRCODE* pTempStr = pStr;
412             while ( nStrLen > 0 )
413             {
414                 if ( *pTempStr == c )
415                     return pTempStr-pStr;
416 
417                 pTempStr++;
418                 nStrLen--;
419             }
420         }
421     }
422     else
423     {
424         const IMPL_RTL_STRCODE* pTempStr = pStr;
425         while ( nStrLen > 0 )
426         {
427             if ( *pTempStr == *pSubStr )
428             {
429                 /* Compare SubString */
430                 if ( nSubLen <= nStrLen )
431                 {
432                     const IMPL_RTL_STRCODE* pTempStr1 = pTempStr;
433                     const IMPL_RTL_STRCODE* pTempStr2 = pSubStr;
434                     sal_Int32               nTempLen = nSubLen;
435                     while ( nTempLen )
436                     {
437                         if ( *pTempStr1 != *pTempStr2 )
438                             break;
439 
440                         pTempStr1++;
441                         pTempStr2++;
442                         nTempLen--;
443                     }
444 
445                     if ( !nTempLen )
446                         return pTempStr-pStr;
447                 }
448                 else
449                     break;
450             }
451 
452             nStrLen--;
453             pTempStr++;
454         }
455     }
456 
457     return -1;
458 }
459 
460 /* ----------------------------------------------------------------------- */
461 
462 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( lastIndexOfStr )( const IMPL_RTL_STRCODE* pStr,
463                                                        const IMPL_RTL_STRCODE* pSubStr )
464 {
465     return IMPL_RTL_STRNAME( lastIndexOfStr_WithLength )( pStr, IMPL_RTL_STRNAME( getLength )( pStr ),
466                                                           pSubStr, IMPL_RTL_STRNAME( getLength )( pSubStr ) );
467 }
468 
469 /* ----------------------------------------------------------------------- */
470 
471 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( lastIndexOfStr_WithLength )( const IMPL_RTL_STRCODE* pStr,
472                                                                   sal_Int32 nStrLen,
473                                                                   const IMPL_RTL_STRCODE* pSubStr,
474                                                                   sal_Int32 nSubLen )
475 {
476     /* faster search for a single character */
477     if ( nSubLen < 2 )
478     {
479         /* an empty SubString is always not foundable */
480         if ( nSubLen == 1 )
481         {
482             IMPL_RTL_STRCODE c = *pSubStr;
483             pStr += nStrLen;
484             while ( nStrLen > 0 )
485             {
486                 nStrLen--;
487                 pStr--;
488 
489                 if ( *pStr == c )
490                     return nStrLen;
491             }
492         }
493     }
494     else
495     {
496         pStr += nStrLen;
497         nStrLen -= nSubLen;
498         pStr -= nSubLen;
499         while ( nStrLen >= 0 )
500         {
501             const IMPL_RTL_STRCODE* pTempStr1 = pStr;
502             const IMPL_RTL_STRCODE* pTempStr2 = pSubStr;
503             sal_Int32               nTempLen = nSubLen;
504             while ( nTempLen )
505             {
506                 if ( *pTempStr1 != *pTempStr2 )
507                     break;
508 
509                 pTempStr1++;
510                 pTempStr2++;
511                 nTempLen--;
512             }
513 
514             if ( !nTempLen )
515                 return nStrLen;
516 
517             nStrLen--;
518             pStr--;
519         }
520     }
521 
522     return -1;
523 }
524 
525 /* ----------------------------------------------------------------------- */
526 
527 void SAL_CALL IMPL_RTL_STRNAME( replaceChar )( IMPL_RTL_STRCODE* pStr,
528                                                IMPL_RTL_STRCODE cOld,
529                                                IMPL_RTL_STRCODE cNew )
530 {
531     while ( *pStr )
532     {
533         if ( *pStr == cOld )
534             *pStr = cNew;
535 
536         pStr++;
537     }
538 }
539 
540 /* ----------------------------------------------------------------------- */
541 
542 void SAL_CALL IMPL_RTL_STRNAME( replaceChar_WithLength )( IMPL_RTL_STRCODE* pStr,
543                                                           sal_Int32 nLen,
544                                                           IMPL_RTL_STRCODE cOld,
545                                                           IMPL_RTL_STRCODE cNew )
546 {
547     while ( nLen > 0 )
548     {
549         if ( *pStr == cOld )
550             *pStr = cNew;
551 
552         pStr++;
553         nLen--;
554     }
555 }
556 
557 /* ----------------------------------------------------------------------- */
558 
559 void SAL_CALL IMPL_RTL_STRNAME( toAsciiLowerCase )( IMPL_RTL_STRCODE* pStr )
560 {
561     while ( *pStr )
562     {
563         /* Between A-Z (65-90), than to lowercase (+32) */
564         if ( (*pStr >= 65) && (*pStr <= 90) )
565             *pStr += 32;
566 
567         pStr++;
568     }
569 }
570 
571 /* ----------------------------------------------------------------------- */
572 
573 void SAL_CALL IMPL_RTL_STRNAME( toAsciiLowerCase_WithLength )( IMPL_RTL_STRCODE* pStr,
574                                                                sal_Int32 nLen )
575 {
576     while ( nLen > 0 )
577     {
578         /* Between A-Z (65-90), than to lowercase (+32) */
579         if ( (*pStr >= 65) && (*pStr <= 90) )
580             *pStr += 32;
581 
582         pStr++;
583         nLen--;
584     }
585 }
586 
587 /* ----------------------------------------------------------------------- */
588 
589 void SAL_CALL IMPL_RTL_STRNAME( toAsciiUpperCase )( IMPL_RTL_STRCODE* pStr )
590 {
591     while ( *pStr )
592     {
593         /* Between a-z (97-122), than to uppercase (-32) */
594         if ( (*pStr >= 97) && (*pStr <= 122) )
595             *pStr -= 32;
596 
597         pStr++;
598     }
599 }
600 
601 /* ----------------------------------------------------------------------- */
602 
603 void SAL_CALL IMPL_RTL_STRNAME( toAsciiUpperCase_WithLength )( IMPL_RTL_STRCODE* pStr,
604                                                                sal_Int32 nLen )
605 {
606     while ( nLen > 0 )
607     {
608         /* Between a-z (97-122), than to uppercase (-32) */
609         if ( (*pStr >= 97) && (*pStr <= 122) )
610             *pStr -= 32;
611 
612         pStr++;
613         nLen--;
614     }
615 }
616 
617 /* ----------------------------------------------------------------------- */
618 
619 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( trim )( IMPL_RTL_STRCODE* pStr )
620 {
621     return IMPL_RTL_STRNAME( trim_WithLength )( pStr, IMPL_RTL_STRNAME( getLength )( pStr ) );
622 }
623 
624 /* ----------------------------------------------------------------------- */
625 
626 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( trim_WithLength )( IMPL_RTL_STRCODE* pStr, sal_Int32 nLen )
627 {
628     sal_Int32 nPreSpaces    = 0;
629     sal_Int32 nPostSpaces   = 0;
630     sal_Int32 nIndex        = nLen-1;
631 
632     while ( (nPreSpaces < nLen) && rtl_ImplIsWhitespace( IMPL_RTL_USTRCODE(*(pStr+nPreSpaces)) ) )
633         nPreSpaces++;
634 
635     while ( (nIndex > nPreSpaces) && rtl_ImplIsWhitespace( IMPL_RTL_USTRCODE(*(pStr+nIndex)) ) )
636     {
637         nPostSpaces++;
638         nIndex--;
639     }
640 
641     if ( nPostSpaces )
642     {
643         nLen -= nPostSpaces;
644         *(pStr+nLen) = 0;
645     }
646 
647     if ( nPreSpaces )
648     {
649         IMPL_RTL_STRCODE* pNewStr = pStr+nPreSpaces;
650 
651         nLen -= nPreSpaces;
652         nIndex = nLen;
653 
654         while ( nIndex )
655         {
656             *pStr = *pNewStr;
657             pStr++;
658             pNewStr++;
659             nIndex--;
660         }
661         *pStr = 0;
662     }
663 
664     return nLen;
665 }
666 
667 /* ----------------------------------------------------------------------- */
668 
669 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( valueOfBoolean )( IMPL_RTL_STRCODE* pStr, sal_Bool b )
670 {
671     if ( b )
672     {
673         *pStr = 't';
674         pStr++;
675         *pStr = 'r';
676         pStr++;
677         *pStr = 'u';
678         pStr++;
679         *pStr = 'e';
680         pStr++;
681         *pStr = 0;
682         return 4;
683     }
684     else
685     {
686         *pStr = 'f';
687         pStr++;
688         *pStr = 'a';
689         pStr++;
690         *pStr = 'l';
691         pStr++;
692         *pStr = 's';
693         pStr++;
694         *pStr = 'e';
695         pStr++;
696         *pStr = 0;
697         return 5;
698     }
699 }
700 
701 /* ----------------------------------------------------------------------- */
702 
703 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( valueOfChar )( IMPL_RTL_STRCODE* pStr,
704                                                     IMPL_RTL_STRCODE c )
705 {
706     *pStr++ = c;
707     *pStr = 0;
708     return 1;
709 }
710 
711 /* ----------------------------------------------------------------------- */
712 
713 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( valueOfInt32 )( IMPL_RTL_STRCODE* pStr,
714                                                      sal_Int32 n,
715                                                      sal_Int16 nRadix )
716 {
717     sal_Char    aBuf[RTL_STR_MAX_VALUEOFINT32];
718     sal_Char*   pBuf = aBuf;
719     sal_Int32   nLen = 0;
720     sal_uInt32  nValue;
721 
722     /* Radix must be valid */
723     if ( (nRadix < RTL_STR_MIN_RADIX) || (nRadix > RTL_STR_MAX_RADIX) )
724         nRadix = 10;
725 
726     /* is value negativ */
727     if ( n < 0 )
728     {
729         *pStr = '-';
730         pStr++;
731         nLen++;
732         nValue = -n; /* FIXME this code is not portable for n == -2147483648
733                         (smallest negative value for sal_Int32) */
734     }
735     else
736         nValue = n;
737 
738     /* create a recursive buffer with all values, except the last one */
739     do
740     {
741         sal_Char nDigit = (sal_Char)(nValue % nRadix);
742         nValue /= nRadix;
743         if ( nDigit > 9 )
744             *pBuf = (nDigit-10) + 'a';
745         else
746             *pBuf = (nDigit + '0' );
747         pBuf++;
748     }
749     while ( nValue > 0 );
750 
751     /* copy the values in the right direction into the destination buffer */
752     do
753     {
754         pBuf--;
755         *pStr = *pBuf;
756         pStr++;
757         nLen++;
758     }
759     while ( pBuf != aBuf );
760     *pStr = 0;
761 
762     return nLen;
763 }
764 
765 /* ----------------------------------------------------------------------- */
766 
767 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( valueOfInt64 )( IMPL_RTL_STRCODE* pStr,
768                                                      sal_Int64 n,
769                                                      sal_Int16 nRadix )
770 {
771     sal_Char    aBuf[RTL_STR_MAX_VALUEOFINT64];
772     sal_Char*   pBuf = aBuf;
773     sal_Int32   nLen = 0;
774     sal_uInt64  nValue;
775 
776     /* Radix must be valid */
777     if ( (nRadix < RTL_STR_MIN_RADIX) || (nRadix > RTL_STR_MAX_RADIX) )
778         nRadix = 10;
779 
780     /* is value negativ */
781     if ( n < 0 )
782     {
783         *pStr = '-';
784         pStr++;
785         nLen++;
786         nValue = -n; /* FIXME this code is not portable for
787                         n == -9223372036854775808 (smallest negative value for
788                         sal_Int64) */
789     }
790     else
791         nValue = n;
792 
793     /* create a recursive buffer with all values, except the last one */
794     do
795     {
796         sal_Char nDigit = (sal_Char)(nValue % nRadix);
797         nValue /= nRadix;
798         if ( nDigit > 9 )
799             *pBuf = (nDigit-10) + 'a';
800         else
801             *pBuf = (nDigit + '0' );
802         pBuf++;
803     }
804     while ( nValue > 0 );
805 
806     /* copy the values in the right direction into the destination buffer */
807     do
808     {
809         pBuf--;
810         *pStr = *pBuf;
811         pStr++;
812         nLen++;
813     }
814     while ( pBuf != aBuf );
815     *pStr = 0;
816 
817     return nLen;
818 }
819 
820 /* ----------------------------------------------------------------------- */
821 
822 sal_Bool SAL_CALL IMPL_RTL_STRNAME( toBoolean )( const IMPL_RTL_STRCODE* pStr )
823 {
824     if ( *pStr == '1' )
825         return sal_True;
826 
827     if ( (*pStr == 'T') || (*pStr == 't') )
828     {
829         pStr++;
830         if ( (*pStr == 'R') || (*pStr == 'r') )
831         {
832             pStr++;
833             if ( (*pStr == 'U') || (*pStr == 'u') )
834             {
835                 pStr++;
836                 if ( (*pStr == 'E') || (*pStr == 'e') )
837                     return sal_True;
838             }
839         }
840     }
841 
842     return sal_False;
843 }
844 
845 /* ----------------------------------------------------------------------- */
846 
847 sal_Int32 SAL_CALL IMPL_RTL_STRNAME( toInt32 )( const IMPL_RTL_STRCODE* pStr,
848                                                 sal_Int16 nRadix )
849 {
850     sal_Bool    bNeg;
851     sal_Int16   nDigit;
852     sal_Int32   n = 0;
853 
854     if ( (nRadix < RTL_STR_MIN_RADIX) || (nRadix > RTL_STR_MAX_RADIX) )
855         nRadix = 10;
856 
857     /* Skip whitespaces */
858     while ( *pStr && rtl_ImplIsWhitespace( IMPL_RTL_USTRCODE( *pStr ) ) )
859         pStr++;
860 
861     if ( *pStr == '-' )
862     {
863         bNeg = sal_True;
864         pStr++;
865     }
866     else
867     {
868         if ( *pStr == '+' )
869             pStr++;
870         bNeg = sal_False;
871     }
872 
873     while ( *pStr )
874     {
875         nDigit = rtl_ImplGetDigit( IMPL_RTL_USTRCODE( *pStr ), nRadix );
876         if ( nDigit < 0 )
877             break;
878 
879         n *= nRadix;
880         n += nDigit;
881 
882         pStr++;
883     }
884 
885     if ( bNeg )
886         return -n;
887     else
888         return n;
889 }
890 
891 /* ----------------------------------------------------------------------- */
892 
893 sal_Int64 SAL_CALL IMPL_RTL_STRNAME( toInt64 )( const IMPL_RTL_STRCODE* pStr,
894                                                 sal_Int16 nRadix )
895 {
896     sal_Bool    bNeg;
897     sal_Int16   nDigit;
898     sal_Int64   n = 0;
899 
900     if ( (nRadix < RTL_STR_MIN_RADIX) || (nRadix > RTL_STR_MAX_RADIX) )
901         nRadix = 10;
902 
903     /* Skip whitespaces */
904     while ( *pStr && rtl_ImplIsWhitespace( IMPL_RTL_USTRCODE( *pStr ) ) )
905         pStr++;
906 
907     if ( *pStr == '-' )
908     {
909         bNeg = sal_True;
910         pStr++;
911     }
912     else
913     {
914         if ( *pStr == '+' )
915             pStr++;
916         bNeg = sal_False;
917     }
918 
919     while ( *pStr )
920     {
921         nDigit = rtl_ImplGetDigit( IMPL_RTL_USTRCODE( *pStr ), nRadix );
922         if ( nDigit < 0 )
923             break;
924 
925         n *= nRadix;
926         n += nDigit;
927 
928         pStr++;
929     }
930 
931     if ( bNeg )
932         return -n;
933     else
934         return n;
935 }
936 
937 /* ======================================================================= */
938 /* Internal String-Class help functions                                    */
939 /* ======================================================================= */
940 
941 static IMPL_RTL_STRINGDATA* IMPL_RTL_STRINGNAME( ImplAlloc )( sal_Int32 nLen )
942 {
943     IMPL_RTL_STRINGDATA * pData
944         = (SAL_INT_CAST(sal_uInt32, nLen)
945            <= ((SAL_MAX_UINT32 - sizeof (IMPL_RTL_STRINGDATA))
946                / sizeof (IMPL_RTL_STRCODE)))
947         ? (IMPL_RTL_STRINGDATA *) rtl_allocateMemory(
948             sizeof (IMPL_RTL_STRINGDATA) + nLen * sizeof (IMPL_RTL_STRCODE))
949         : NULL;
950     if (pData != NULL) {
951         pData->refCount = 1;
952         pData->length = nLen;
953         pData->buffer[nLen] = 0;
954     }
955     return pData;
956 }
957 
958 /* ----------------------------------------------------------------------- */
959 
960 static IMPL_RTL_STRCODE* IMPL_RTL_STRINGNAME( ImplNewCopy )( IMPL_RTL_STRINGDATA** ppThis,
961                                                              IMPL_RTL_STRINGDATA* pStr,
962                                                              sal_Int32 nCount )
963 {
964     IMPL_RTL_STRCODE*       pDest;
965     const IMPL_RTL_STRCODE* pSrc;
966     IMPL_RTL_STRINGDATA*    pData = IMPL_RTL_STRINGNAME( ImplAlloc )( pStr->length );
967     OSL_ASSERT(pData != NULL);
968 
969     pDest   = pData->buffer;
970     pSrc    = pStr->buffer;
971     while ( nCount > 0 )
972     {
973         *pDest = *pSrc;
974         pDest++;
975         pSrc++;
976         nCount--;
977     }
978 
979     *ppThis = pData;
980     return pDest;
981 }
982 
983 /* ======================================================================= */
984 /* String-Class functions                                                  */
985 /* ======================================================================= */
986 
987 #define IMPL_RTL_AQUIRE( pThis )                                \
988 {                                                               \
989     if (!SAL_STRING_IS_STATIC (pThis))                          \
990         osl_incrementInterlockedCount( &((pThis)->refCount) );  \
991 }
992 
993 /* ----------------------------------------------------------------------- */
994 
995 void SAL_CALL IMPL_RTL_STRINGNAME( acquire )( IMPL_RTL_STRINGDATA* pThis )
996 {
997     IMPL_RTL_AQUIRE( pThis );
998 }
999 
1000 /* ----------------------------------------------------------------------- */
1001 
1002 void SAL_CALL IMPL_RTL_STRINGNAME( release )( IMPL_RTL_STRINGDATA* pThis )
1003 {
1004     if (SAL_STRING_IS_STATIC (pThis))
1005         return;
1006 
1007 /* OString doesn't have an 'intern' */
1008 #ifdef IMPL_RTL_INTERN
1009     if (SAL_STRING_IS_INTERN (pThis))
1010     {
1011         internRelease (pThis);
1012         return;
1013     }
1014 #endif
1015 
1016     if ( pThis->refCount == 1 ||
1017          !osl_decrementInterlockedCount( &(pThis->refCount) ) )
1018     {
1019         rtl_freeMemory( pThis );
1020     }
1021 }
1022 
1023 /* ----------------------------------------------------------------------- */
1024 
1025 void SAL_CALL IMPL_RTL_STRINGNAME( new )( IMPL_RTL_STRINGDATA** ppThis )
1026 {
1027     if ( *ppThis)
1028         IMPL_RTL_STRINGNAME( release )( *ppThis );
1029 
1030     *ppThis = (IMPL_RTL_STRINGDATA*) (&IMPL_RTL_EMPTYSTRING);
1031     IMPL_RTL_AQUIRE( *ppThis );
1032 }
1033 
1034 /* ----------------------------------------------------------------------- */
1035 
1036 void SAL_CALL IMPL_RTL_STRINGNAME( new_WithLength )( IMPL_RTL_STRINGDATA** ppThis, sal_Int32 nLen )
1037 {
1038     if ( nLen <= 0 )
1039         IMPL_RTL_STRINGNAME( new )( ppThis );
1040     else
1041     {
1042         if ( *ppThis)
1043             IMPL_RTL_STRINGNAME( release )( *ppThis );
1044 
1045         *ppThis = IMPL_RTL_STRINGNAME( ImplAlloc )( nLen );
1046         OSL_ASSERT(*ppThis != NULL);
1047         (*ppThis)->length   = 0;
1048 
1049         {
1050         IMPL_RTL_STRCODE* pTempStr = (*ppThis)->buffer;
1051         while ( nLen >= 0 )
1052         {
1053             *pTempStr = 0;
1054             pTempStr++;
1055             nLen--;
1056         }
1057         }
1058     }
1059 }
1060 
1061 /* ----------------------------------------------------------------------- */
1062 
1063 void SAL_CALL IMPL_RTL_STRINGNAME( newFromString )( IMPL_RTL_STRINGDATA** ppThis,
1064                                                     const IMPL_RTL_STRINGDATA* pStr )
1065 {
1066     IMPL_RTL_STRINGDATA* pOrg;
1067 
1068     if ( !pStr->length )
1069     {
1070         IMPL_RTL_STRINGNAME( new )( ppThis );
1071         return;
1072     }
1073 
1074     pOrg = *ppThis;
1075     *ppThis = IMPL_RTL_STRINGNAME( ImplAlloc )( pStr->length );
1076     OSL_ASSERT(*ppThis != NULL);
1077     rtl_str_ImplCopy( (*ppThis)->buffer, pStr->buffer, pStr->length );
1078 
1079     /* must be done at least, if pStr == *ppThis */
1080     if ( pOrg )
1081         IMPL_RTL_STRINGNAME( release )( pOrg );
1082 }
1083 
1084 /* ----------------------------------------------------------------------- */
1085 
1086 void SAL_CALL IMPL_RTL_STRINGNAME( newFromStr )( IMPL_RTL_STRINGDATA** ppThis,
1087                                                  const IMPL_RTL_STRCODE* pCharStr )
1088 {
1089     IMPL_RTL_STRCODE*       pBuffer;
1090     IMPL_RTL_STRINGDATA*    pOrg;
1091     sal_Int32               nLen;
1092 
1093     if ( pCharStr )
1094     {
1095         const IMPL_RTL_STRCODE* pTempStr = pCharStr;
1096         while( *pTempStr )
1097             pTempStr++;
1098         nLen = pTempStr-pCharStr;
1099     }
1100     else
1101         nLen = 0;
1102 
1103     if ( !nLen )
1104     {
1105         IMPL_RTL_STRINGNAME( new )( ppThis );
1106         return;
1107     }
1108 
1109     pOrg = *ppThis;
1110     *ppThis = IMPL_RTL_STRINGNAME( ImplAlloc )( nLen );
1111     OSL_ASSERT(*ppThis != NULL);
1112     pBuffer = (*ppThis)->buffer;
1113     do
1114     {
1115         *pBuffer = *pCharStr;
1116         pBuffer++;
1117         pCharStr++;
1118     }
1119     while ( *pCharStr );
1120 
1121     /* must be done at least, if pCharStr == *ppThis */
1122     if ( pOrg )
1123         IMPL_RTL_STRINGNAME( release )( pOrg );
1124 }
1125 
1126 /* ----------------------------------------------------------------------- */
1127 
1128 void SAL_CALL IMPL_RTL_STRINGNAME( newFromStr_WithLength )( IMPL_RTL_STRINGDATA** ppThis,
1129                                                             const IMPL_RTL_STRCODE* pCharStr,
1130                                                             sal_Int32 nLen )
1131 {
1132     IMPL_RTL_STRINGDATA* pOrg;
1133 
1134     if ( !pCharStr || (nLen <= 0) )
1135     {
1136         IMPL_RTL_STRINGNAME( new )( ppThis );
1137         return;
1138     }
1139 
1140     pOrg = *ppThis;
1141     *ppThis = IMPL_RTL_STRINGNAME( ImplAlloc )( nLen );
1142     OSL_ASSERT(*ppThis != NULL);
1143     rtl_str_ImplCopy( (*ppThis)->buffer, pCharStr, nLen );
1144 
1145     /* must be done at least, if pCharStr == *ppThis */
1146     if ( pOrg )
1147         IMPL_RTL_STRINGNAME( release )( pOrg );
1148 }
1149 
1150 /* ----------------------------------------------------------------------- */
1151 
1152 void SAL_CALL IMPL_RTL_STRINGNAME( assign )( IMPL_RTL_STRINGDATA** ppThis,
1153                                              IMPL_RTL_STRINGDATA* pStr )
1154 {
1155     /* must be done at first, if pStr == *ppThis */
1156     IMPL_RTL_AQUIRE( pStr );
1157 
1158     if ( *ppThis )
1159         IMPL_RTL_STRINGNAME( release )( *ppThis );
1160 
1161     *ppThis = pStr;
1162 }
1163 
1164 /* ----------------------------------------------------------------------- */
1165 
1166 sal_Int32 SAL_CALL IMPL_RTL_STRINGNAME( getLength )( const IMPL_RTL_STRINGDATA* pThis )
1167 {
1168     return pThis->length;
1169 }
1170 
1171 /* ----------------------------------------------------------------------- */
1172 
1173 IMPL_RTL_STRCODE* SAL_CALL IMPL_RTL_STRINGNAME( getStr )( IMPL_RTL_STRINGDATA * pThis )
1174 {
1175     return pThis->buffer;
1176 }
1177 
1178 /* ----------------------------------------------------------------------- */
1179 
1180 void SAL_CALL IMPL_RTL_STRINGNAME( newConcat )( IMPL_RTL_STRINGDATA** ppThis,
1181                                                 IMPL_RTL_STRINGDATA* pLeft,
1182                                                 IMPL_RTL_STRINGDATA* pRight )
1183 {
1184     IMPL_RTL_STRINGDATA* pOrg = *ppThis;
1185 
1186     /* Test for 0-Pointer - if not, change newReplaceStrAt! */
1187     if ( !pRight || !pRight->length )
1188     {
1189         *ppThis = pLeft;
1190         IMPL_RTL_AQUIRE( pLeft );
1191     }
1192     else if ( !pLeft || !pLeft->length )
1193     {
1194         *ppThis = pRight;
1195         IMPL_RTL_AQUIRE( pRight );
1196     }
1197     else
1198     {
1199         IMPL_RTL_STRINGDATA* pTempStr = IMPL_RTL_STRINGNAME( ImplAlloc )( pLeft->length + pRight->length );
1200         OSL_ASSERT(pTempStr != NULL);
1201         rtl_str_ImplCopy( pTempStr->buffer, pLeft->buffer, pLeft->length );
1202         rtl_str_ImplCopy( pTempStr->buffer+pLeft->length, pRight->buffer, pRight->length );
1203         *ppThis = pTempStr;
1204     }
1205 
1206     /* must be done at least, if left or right == *ppThis */
1207     if ( pOrg )
1208         IMPL_RTL_STRINGNAME( release )( pOrg );
1209 }
1210 
1211 /* ----------------------------------------------------------------------- */
1212 
1213 void SAL_CALL IMPL_RTL_STRINGNAME( newReplaceStrAt )( IMPL_RTL_STRINGDATA** ppThis,
1214                                                       IMPL_RTL_STRINGDATA* pStr,
1215                                                       sal_Int32 nIndex,
1216                                                       sal_Int32 nCount,
1217                                                       IMPL_RTL_STRINGDATA* pNewSubStr )
1218 {
1219     /* Append? */
1220     if ( nIndex >= pStr->length )
1221     {
1222         /* newConcat test, if pNewSubStr is 0 */
1223         IMPL_RTL_STRINGNAME( newConcat )( ppThis, pStr, pNewSubStr );
1224         return;
1225     }
1226 
1227     /* negativ index? */
1228     if ( nIndex < 0 )
1229     {
1230         nCount -= nIndex;
1231         nIndex = 0;
1232     }
1233 
1234     /* not more than the String length could be deleted */
1235     if ( nCount >= pStr->length-nIndex )
1236     {
1237         nCount = pStr->length-nIndex;
1238 
1239         /* Assign of NewSubStr? */
1240         if ( !nIndex && (nCount >= pStr->length) )
1241         {
1242             if ( !pNewSubStr )
1243                 IMPL_RTL_STRINGNAME( new )( ppThis );
1244             else
1245                 IMPL_RTL_STRINGNAME( assign )( ppThis, pNewSubStr );
1246             return;
1247         }
1248     }
1249 
1250     /* Assign of Str? */
1251     if ( !nCount && (!pNewSubStr || !pNewSubStr->length) )
1252     {
1253         IMPL_RTL_STRINGNAME( assign )( ppThis, pStr );
1254         return;
1255     }
1256 
1257     {
1258     IMPL_RTL_STRINGDATA*    pOrg = *ppThis;
1259     IMPL_RTL_STRCODE*       pBuffer;
1260     sal_Int32               nNewLen;
1261 
1262     /* Calculate length of the new string */
1263     nNewLen = pStr->length-nCount;
1264     if ( pNewSubStr )
1265         nNewLen += pNewSubStr->length;
1266 
1267     /* Alloc New Buffer */
1268     *ppThis = IMPL_RTL_STRINGNAME( ImplAlloc )( nNewLen );
1269     OSL_ASSERT(*ppThis != NULL);
1270     pBuffer = (*ppThis)->buffer;
1271     if ( nIndex )
1272     {
1273         rtl_str_ImplCopy( pBuffer, pStr->buffer, nIndex );
1274         pBuffer += nIndex;
1275     }
1276     if ( pNewSubStr && pNewSubStr->length )
1277     {
1278         rtl_str_ImplCopy( pBuffer, pNewSubStr->buffer, pNewSubStr->length );
1279         pBuffer += pNewSubStr->length;
1280     }
1281     rtl_str_ImplCopy( pBuffer, pStr->buffer+nIndex+nCount, pStr->length-nIndex-nCount );
1282 
1283     /* must be done at least, if pStr or pNewSubStr == *ppThis */
1284     if ( pOrg )
1285         IMPL_RTL_STRINGNAME( release )( pOrg );
1286     }
1287 }
1288 
1289 /* ----------------------------------------------------------------------- */
1290 
1291 void SAL_CALL IMPL_RTL_STRINGNAME( newReplace )( IMPL_RTL_STRINGDATA** ppThis,
1292                                                  IMPL_RTL_STRINGDATA* pStr,
1293                                                  IMPL_RTL_STRCODE cOld,
1294                                                  IMPL_RTL_STRCODE cNew )
1295 {
1296     IMPL_RTL_STRINGDATA*    pOrg        = *ppThis;
1297     int                     bChanged    = 0;
1298     sal_Int32               nLen        = pStr->length;
1299     const IMPL_RTL_STRCODE* pCharStr    = pStr->buffer;
1300 
1301     while ( nLen > 0 )
1302     {
1303         if ( *pCharStr == cOld )
1304         {
1305             /* Copy String */
1306             IMPL_RTL_STRCODE* pNewCharStr = IMPL_RTL_STRINGNAME( ImplNewCopy )( ppThis, pStr, pCharStr-pStr->buffer );
1307 
1308             /* replace/copy rest of the string */
1309             if ( pNewCharStr )
1310             {
1311                 *pNewCharStr = cNew;
1312                 pNewCharStr++;
1313                 pCharStr++;
1314                 nLen--;
1315 
1316                 while ( nLen > 0 )
1317                 {
1318                     if ( *pCharStr == cOld )
1319                         *pNewCharStr = cNew;
1320                     else
1321                         *pNewCharStr = *pCharStr;
1322 
1323                     pNewCharStr++;
1324                     pCharStr++;
1325                     nLen--;
1326                 }
1327             }
1328 
1329             bChanged = 1;
1330             break;
1331         }
1332 
1333         pCharStr++;
1334         nLen--;
1335     }
1336 
1337     if ( !bChanged )
1338     {
1339         *ppThis = pStr;
1340         IMPL_RTL_AQUIRE( pStr );
1341     }
1342 
1343     /* must be done at least, if pStr == *ppThis */
1344     if ( pOrg )
1345         IMPL_RTL_STRINGNAME( release )( pOrg );
1346 }
1347 
1348 /* ----------------------------------------------------------------------- */
1349 
1350 void SAL_CALL IMPL_RTL_STRINGNAME( newToAsciiLowerCase )( IMPL_RTL_STRINGDATA** ppThis,
1351                                                           IMPL_RTL_STRINGDATA* pStr )
1352 {
1353     IMPL_RTL_STRINGDATA*    pOrg        = *ppThis;
1354     int                     bChanged    = 0;
1355     sal_Int32               nLen        = pStr->length;
1356     const IMPL_RTL_STRCODE* pCharStr    = pStr->buffer;
1357 
1358     while ( nLen > 0 )
1359     {
1360         /* Between A-Z (65-90), than to lowercase (+32) */
1361         if ( (*pCharStr >= 65) && (*pCharStr <= 90) )
1362         {
1363             /* Copy String */
1364             IMPL_RTL_STRCODE* pNewCharStr = IMPL_RTL_STRINGNAME( ImplNewCopy )( ppThis, pStr, pCharStr-pStr->buffer );
1365 
1366             /* replace/copy rest of the string */
1367             if ( pNewCharStr )
1368             {
1369                 /* to lowercase (+32) */
1370                 *pNewCharStr = *pCharStr+32;
1371                 pNewCharStr++;
1372                 pCharStr++;
1373                 nLen--;
1374 
1375                 while ( nLen > 0 )
1376                 {
1377                     /* Between A-Z (65-90), than to lowercase (+32) */
1378                     if ( (*pCharStr >= 65) && (*pCharStr <= 90) )
1379                         *pNewCharStr = *pCharStr+32;
1380                     else
1381                         *pNewCharStr = *pCharStr;
1382 
1383                     pNewCharStr++;
1384                     pCharStr++;
1385                     nLen--;
1386                 }
1387             }
1388 
1389             bChanged = 1;
1390             break;
1391         }
1392 
1393         pCharStr++;
1394         nLen--;
1395     }
1396 
1397     if ( !bChanged )
1398     {
1399         *ppThis = pStr;
1400         IMPL_RTL_AQUIRE( pStr );
1401     }
1402 
1403     /* must be done at least, if pStr == *ppThis */
1404     if ( pOrg )
1405         IMPL_RTL_STRINGNAME( release )( pOrg );
1406 }
1407 
1408 /* ----------------------------------------------------------------------- */
1409 
1410 void SAL_CALL IMPL_RTL_STRINGNAME( newToAsciiUpperCase )( IMPL_RTL_STRINGDATA** ppThis,
1411                                                           IMPL_RTL_STRINGDATA* pStr )
1412 {
1413     IMPL_RTL_STRINGDATA*    pOrg        = *ppThis;
1414     int                     bChanged    = 0;
1415     sal_Int32               nLen        = pStr->length;
1416     const IMPL_RTL_STRCODE* pCharStr    = pStr->buffer;
1417 
1418     while ( nLen > 0 )
1419     {
1420         /* Between a-z (97-122), than to uppercase (-32) */
1421         if ( (*pCharStr >= 97) && (*pCharStr <= 122) )
1422         {
1423             /* Copy String */
1424             IMPL_RTL_STRCODE* pNewCharStr = IMPL_RTL_STRINGNAME( ImplNewCopy )( ppThis, pStr, pCharStr-pStr->buffer );
1425 
1426             /* replace/copy rest of the string */
1427             if ( pNewCharStr )
1428             {
1429                 /* to uppercase (-32) */
1430                 *pNewCharStr = *pCharStr-32;
1431                 pNewCharStr++;
1432                 pCharStr++;
1433                 nLen--;
1434 
1435                 while ( nLen > 0 )
1436                 {
1437                     /* Between a-z (97-122), than to uppercase (-32) */
1438                     if ( (*pCharStr >= 97) && (*pCharStr <= 122) )
1439                         *pNewCharStr = *pCharStr-32;
1440                     else
1441                         *pNewCharStr = *pCharStr;
1442 
1443                     pNewCharStr++;
1444                     pCharStr++;
1445                     nLen--;
1446                 }
1447             }
1448 
1449             bChanged = 1;
1450             break;
1451         }
1452 
1453         pCharStr++;
1454         nLen--;
1455     }
1456 
1457     if ( !bChanged )
1458     {
1459         *ppThis = pStr;
1460         IMPL_RTL_AQUIRE( pStr );
1461     }
1462 
1463     /* must be done at least, if pStr == *ppThis */
1464     if ( pOrg )
1465         IMPL_RTL_STRINGNAME( release )( pOrg );
1466 }
1467 
1468 /* ----------------------------------------------------------------------- */
1469 
1470 void SAL_CALL IMPL_RTL_STRINGNAME( newTrim )( IMPL_RTL_STRINGDATA** ppThis,
1471                                               IMPL_RTL_STRINGDATA* pStr )
1472 {
1473     IMPL_RTL_STRINGDATA*    pOrg        = *ppThis;
1474     const IMPL_RTL_STRCODE* pCharStr    = pStr->buffer;
1475     sal_Int32               nPreSpaces  = 0;
1476     sal_Int32               nPostSpaces = 0;
1477     sal_Int32               nLen        = pStr->length;
1478     sal_Int32               nIndex      = nLen-1;
1479 
1480     while ( (nPreSpaces < nLen) && rtl_ImplIsWhitespace( IMPL_RTL_USTRCODE(*(pCharStr+nPreSpaces)) ) )
1481         nPreSpaces++;
1482 
1483     while ( (nIndex > nPreSpaces) && rtl_ImplIsWhitespace( IMPL_RTL_USTRCODE(*(pCharStr+nIndex)) ) )
1484     {
1485         nPostSpaces++;
1486         nIndex--;
1487     }
1488 
1489     if ( !nPreSpaces && !nPostSpaces )
1490     {
1491         *ppThis = pStr;
1492         IMPL_RTL_AQUIRE( pStr );
1493     }
1494     else
1495     {
1496         nLen -= nPostSpaces+nPreSpaces;
1497         *ppThis = IMPL_RTL_STRINGNAME( ImplAlloc )( nLen );
1498         OSL_ASSERT(*ppThis != NULL);
1499         if ( *ppThis )
1500             rtl_str_ImplCopy( (*ppThis)->buffer, pStr->buffer+nPreSpaces, nLen );
1501     }
1502 
1503     /* must be done at least, if pStr == *ppThis */
1504     if ( pOrg )
1505         IMPL_RTL_STRINGNAME( release )( pOrg );
1506 }
1507 
1508 /* ----------------------------------------------------------------------- */
1509 
1510 sal_Int32 SAL_CALL IMPL_RTL_STRINGNAME( getToken )( IMPL_RTL_STRINGDATA** ppThis,
1511                                                     IMPL_RTL_STRINGDATA* pStr,
1512                                                     sal_Int32 nToken,
1513                                                     IMPL_RTL_STRCODE cTok,
1514                                                     sal_Int32 nIndex )
1515 {
1516     const IMPL_RTL_STRCODE* pCharStr        = pStr->buffer;
1517     const IMPL_RTL_STRCODE* pCharStrStart;
1518     const IMPL_RTL_STRCODE* pOrgCharStr;
1519     sal_Int32               nLen            = pStr->length-nIndex;
1520     sal_Int32               nTokCount       = 0;
1521 
1522     // Set ppThis to an empty string and return -1 if either nToken or nIndex is
1523     // negative:
1524     if (nIndex < 0) {
1525         nToken = -1;
1526     }
1527 
1528     pCharStr += nIndex;
1529     pOrgCharStr = pCharStr;
1530     pCharStrStart = pCharStr;
1531     while ( nLen > 0 )
1532     {
1533         if ( *pCharStr == cTok )
1534         {
1535             nTokCount++;
1536 
1537             if ( nTokCount == nToken )
1538                 pCharStrStart = pCharStr+1;
1539             else
1540             {
1541                 if ( nTokCount > nToken )
1542                     break;
1543             }
1544         }
1545 
1546         pCharStr++;
1547         nLen--;
1548     }
1549 
1550     if ( (nToken < 0) || (nTokCount < nToken) || (pCharStr == pCharStrStart) )
1551     {
1552         IMPL_RTL_STRINGNAME( new )( ppThis );
1553         if( (nToken < 0) || (nTokCount < nToken ) )
1554             return -1;
1555         else if( nLen > 0 )
1556             return nIndex+(pCharStr-pOrgCharStr)+1;
1557         else return -1;
1558     }
1559     else
1560     {
1561         IMPL_RTL_STRINGNAME( newFromStr_WithLength )( ppThis, pCharStrStart, pCharStr-pCharStrStart );
1562         if ( nLen )
1563             return nIndex+(pCharStr-pOrgCharStr)+1;
1564         else
1565             return -1;
1566     }
1567 }
1568