Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #ifndef _STRING_HXX
21 : #define _STRING_HXX
22 :
23 : #include <tools/solar.h>
24 : #include <osl/thread.h>
25 : #include <rtl/textenc.h>
26 : #include <rtl/textcvt.h>
27 : #include <rtl/ustrbuf.h>
28 : #include <rtl/string.hxx>
29 : #include <rtl/ustring.hxx>
30 : #include "tools/toolsdllapi.h"
31 : #include "tools/lineend.hxx"
32 :
33 : /*******************************************************************************
34 : *
35 : * THIS CODE IS DEPRECATED. DO NOT USE IT IN ANY NEW CODE.
36 : *
37 : * Use the string classes in rtl/ustring.hxx and rtl/ustrbuf.hxx (and
38 : * rtl/string.hxx and rtl/strbuf.hxx for byte-sized strings) instead. If you
39 : * feel functionality missing from those string classes, please request
40 : * improvements on discuss@openoffice.org.
41 : *
42 : * There will not be any fixes to the code here.
43 : ******************************************************************************/
44 :
45 : class ResId;
46 : class String;
47 : class UniString;
48 :
49 : #define BYTESTRING_TO_UNISTRING_CVTFLAGS (RTL_TEXTTOUNICODE_FLAGS_UNDEFINED_MAPTOPRIVATE |\
50 : RTL_TEXTTOUNICODE_FLAGS_MBUNDEFINED_DEFAULT |\
51 : RTL_TEXTTOUNICODE_FLAGS_INVALID_DEFAULT)
52 :
53 : // CharSet
54 :
55 : #ifndef ENUM_CHARSET_DECLARED
56 : #define ENUM_CHARSET_DECLARED
57 :
58 : typedef rtl_TextEncoding CharSet;
59 :
60 : #endif
61 :
62 : // String-Types
63 :
64 : #ifdef STRING32
65 : #define STRING_NOTFOUND ((xub_StrLen)0x7FFFFFFF)
66 : #define STRING_MATCH ((xub_StrLen)0x7FFFFFFF)
67 : #define STRING_LEN ((xub_StrLen)0x7FFFFFFF)
68 : #define STRING_MAXLEN ((xub_StrLen)0x7FFFFFFF)
69 : #else
70 : #define STRING_NOTFOUND ((xub_StrLen)0xFFFF)
71 : #define STRING_MATCH ((xub_StrLen)0xFFFF)
72 : #define STRING_LEN ((xub_StrLen)0xFFFF)
73 : #define STRING_MAXLEN ((xub_StrLen)0xFFFF)
74 : #endif
75 :
76 : enum StringCompare { COMPARE_LESS = -1, COMPARE_EQUAL = 0, COMPARE_GREATER = 1 };
77 :
78 : //Internal String data
79 :
80 : // Data used for the management of this String
81 : // use only for debugging purposes (never assign to String directly!)
82 :
83 : #ifdef SAL_W32
84 : #pragma pack(push, 4)
85 : #endif
86 :
87 : typedef struct _UniStringData
88 : {
89 : sal_Int32 mnRefCount; // reference counter
90 : sal_Int32 mnLen; // Length of the String
91 : sal_Unicode maStr[1]; // CharArray (String)
92 : } UniStringData;
93 :
94 : #ifdef SAL_W32
95 : #pragma pack(pop)
96 : #endif
97 :
98 : // UniString
99 :
100 : class TOOLS_DLLPUBLIC SAL_WARN_UNUSED UniString
101 : {
102 : private:
103 : UniStringData* mpData;
104 :
105 : TOOLS_DLLPRIVATE inline void ImplCopyData();
106 : TOOLS_DLLPRIVATE inline sal_Unicode * ImplCopyStringData(sal_Unicode *);
107 :
108 : UniString( const int* pDummy ); // not implemented: to prevent UniString( NULL )
109 : UniString(int); // not implemented; to detect misuses of
110 : // UniString(sal_Unicode)
111 : void Assign(int); // not implemented; to detect misuses of
112 : // Assign(sal_Unicode)
113 : void operator =(int); // not implemented; to detect misuses
114 : // of operator =(sal_Unicode)
115 : void Append(int); // not implemented; to detect misuses of
116 : // Append(sal_Unicode)
117 : void operator +=(int); // not implemented; to detect misuses
118 : // of operator +=(sal_Unicode)
119 :
120 : //detect and reject use of RTL_CONSTASCII_STRINGPARAM instead of RTL_CONSTASCII_USTRINGPARAM
121 : TOOLS_DLLPRIVATE UniString( const sal_Char*, sal_Int32 );
122 :
123 : //detect and reject wrong way to attempt to create a UniString from a substring of
124 : //a OString
125 : TOOLS_DLLPRIVATE UniString(const OString& rByteStr, xub_StrLen nPos, xub_StrLen nLen,
126 : sal_uInt32 nCvtFlags = BYTESTRING_TO_UNISTRING_CVTFLAGS);
127 :
128 : //no longer implemented
129 : TOOLS_DLLPRIVATE UniString( const OString& rByteStr,
130 : rtl_TextEncoding eTextEncoding,
131 : sal_uInt32 nCvtFlags = BYTESTRING_TO_UNISTRING_CVTFLAGS );
132 : TOOLS_DLLPRIVATE UniString( const sal_Unicode* pCharStr );
133 : TOOLS_DLLPRIVATE UniString( const sal_Unicode* pCharStr, xub_StrLen nLen );
134 : TOOLS_DLLPRIVATE UniString( sal_Unicode c );
135 : TOOLS_DLLPRIVATE UniString& Assign( const sal_Unicode* pCharStr, xub_StrLen nLen );
136 : TOOLS_DLLPRIVATE UniString& Expand( xub_StrLen nCount, sal_Unicode cExpandChar );
137 : public:
138 : UniString();
139 : UniString( const ResId& rResId );
140 : UniString( const UniString& rStr );
141 : UniString( const UniString& rStr, xub_StrLen nPos, xub_StrLen nLen );
142 : UniString( const OUString& rStr );
143 : UniString(char c); // ...but allow "UniString('a')"
144 : UniString( const sal_Char* pByteStr,
145 : rtl_TextEncoding eTextEncoding,
146 : sal_uInt32 nCvtFlags = BYTESTRING_TO_UNISTRING_CVTFLAGS );
147 : UniString( const sal_Char* pByteStr, xub_StrLen nLen,
148 : rtl_TextEncoding eTextEncoding,
149 : sal_uInt32 nCvtFlags = BYTESTRING_TO_UNISTRING_CVTFLAGS );
150 : ~UniString();
151 :
152 17200590 : operator OUString () const
153 : {
154 : return OUString( rtl_uStringBuffer_refReturn(
155 17200590 : reinterpret_cast<rtl_uString*>(mpData)), SAL_NO_ACQUIRE );
156 : }
157 :
158 : #ifdef RTL_FAST_STRING
159 : template< typename T1, typename T2 >
160 701 : UniString( const rtl::OUStringConcat< T1, T2 >& concat )
161 701 : : mpData(NULL) { Assign( OUString( concat )); }
162 : template< typename T1, typename T2 >
163 41 : UniString& operator =( const rtl::OUStringConcat< T1, T2 >& concat )
164 41 : { return Assign( OUString( concat )); }
165 : template< typename T1, typename T2 >
166 12 : UniString& operator +=( const rtl::OUStringConcat< T1, T2 >& concat )
167 12 : { return Append( UniString( concat ) ); }
168 : #endif
169 :
170 : static const UniString& EmptyString();
171 : sal_Int32 ToInt32() const;
172 : sal_Int64 ToInt64() const;
173 :
174 : UniString& Assign( const UniString& rStr );
175 : UniString& Assign( const OUString& rStr );
176 : UniString& Assign( const sal_Unicode* pCharStr );
177 : UniString& Assign( sal_Unicode c );
178 14 : inline UniString & Assign(char c) // ...but allow "Assign('a')"
179 14 : { return Assign(static_cast< sal_Unicode >(c)); }
180 : UniString& AssignAscii( const sal_Char* pAsciiStr );
181 : UniString& AssignAscii( const sal_Char* pAsciiStr, xub_StrLen nLen );
182 2427770 : UniString& operator =( const UniString& rStr )
183 2427770 : { return Assign( rStr ); }
184 2654135 : UniString& operator =( const OUString& rStr )
185 2654135 : { return Assign( rStr ); }
186 77801 : UniString& operator =( const sal_Unicode* pCharStr )
187 77801 : { return Assign( pCharStr ); }
188 94 : UniString& operator =( sal_Unicode c )
189 94 : { return Assign( c ); }
190 83 : inline UniString & operator =(char c) // ...but allow "= 'a'"
191 83 : { return operator =(static_cast< sal_Unicode >(c)); }
192 :
193 : UniString& Append( const UniString& rStr );
194 : UniString& Append( const sal_Unicode* pCharStr );
195 : UniString& Append( const sal_Unicode* pCharStr, xub_StrLen nLen );
196 : UniString& Append( sal_Unicode c );
197 1469 : inline UniString & Append(char c) // ...but allow "Append('a')"
198 1469 : { return Append(static_cast< sal_Unicode >(c)); }
199 : UniString& AppendAscii( const sal_Char* pAsciiStr );
200 : UniString& AppendAscii( const sal_Char* pAsciiStr, xub_StrLen nLen );
201 296586 : UniString& operator +=( const UniString& rStr )
202 296586 : { return Append( rStr ); }
203 257711 : UniString& operator +=( const OUString& rStr )
204 257711 : { return Append( UniString(rStr) ); }
205 0 : UniString& operator +=( const sal_Unicode* pCharStr )
206 0 : { return Append( pCharStr ); }
207 85287 : UniString& operator +=( sal_Unicode c )
208 85287 : { return Append( c ); }
209 39619 : inline UniString & operator +=(char c) // ...but allow "+= 'a'"
210 39619 : { return operator +=(static_cast< sal_Unicode >(c)); }
211 :
212 : void SetChar( xub_StrLen nIndex, sal_Unicode c );
213 2179221 : sal_Unicode GetChar( xub_StrLen nIndex ) const
214 2179221 : { return mpData->maStr[nIndex]; }
215 :
216 12591029 : xub_StrLen Len() const { return (xub_StrLen)mpData->mnLen; }
217 :
218 : UniString& Insert( const UniString& rStr, xub_StrLen nIndex = STRING_LEN );
219 : UniString& Insert( const UniString& rStr, xub_StrLen nPos, xub_StrLen nLen,
220 : xub_StrLen nIndex = STRING_LEN );
221 : UniString& Insert( sal_Unicode c, xub_StrLen nIndex = STRING_LEN );
222 : UniString& InsertAscii( const sal_Char* pAsciiStr, xub_StrLen nIndex = STRING_LEN );
223 : UniString& Replace( xub_StrLen nIndex, xub_StrLen nLen, const UniString& rStr );
224 : UniString& ReplaceAscii( xub_StrLen nIndex, xub_StrLen nLen,
225 : const sal_Char* pAsciiStr, xub_StrLen nStrLen = STRING_LEN );
226 : UniString& Erase( xub_StrLen nIndex = 0, xub_StrLen nCount = STRING_LEN );
227 : UniString Copy( xub_StrLen nIndex = 0, xub_StrLen nCount = STRING_LEN ) const;
228 :
229 : UniString& ToLowerAscii();
230 : UniString& ToUpperAscii();
231 :
232 : StringCompare CompareTo( const UniString& rStr,
233 : xub_StrLen nLen = STRING_LEN ) const;
234 : StringCompare CompareToAscii( const sal_Char* pAsciiStr,
235 : xub_StrLen nLen = STRING_LEN ) const;
236 : StringCompare CompareIgnoreCaseToAscii( const UniString& rStr,
237 : xub_StrLen nLen = STRING_LEN ) const;
238 : StringCompare CompareIgnoreCaseToAscii( const sal_Char* pAsciiStr,
239 : xub_StrLen nLen = STRING_LEN ) const;
240 : sal_Bool Equals( const UniString& rStr ) const;
241 : sal_Bool EqualsAscii( const sal_Char* pAsciiStr ) const;
242 : sal_Bool EqualsIgnoreCaseAscii( const UniString& rStr ) const;
243 : sal_Bool EqualsIgnoreCaseAscii( const sal_Unicode* pCharStr ) const;
244 : sal_Bool EqualsIgnoreCaseAscii( const sal_Char* pAsciiStr ) const;
245 : sal_Bool Equals( const UniString& rStr,
246 : xub_StrLen nIndex, xub_StrLen nLen ) const;
247 : sal_Bool Equals( const sal_Unicode* pCharStr,
248 : xub_StrLen nIndex, xub_StrLen nLen ) const;
249 : sal_Bool EqualsAscii( const sal_Char* pAsciiStr,
250 : xub_StrLen nIndex, xub_StrLen nLen ) const;
251 : sal_Bool EqualsIgnoreCaseAscii( const UniString& rStr,
252 : xub_StrLen nIndex, xub_StrLen nLen ) const;
253 : sal_Bool EqualsIgnoreCaseAscii( const sal_Char* pAsciiStr,
254 : xub_StrLen nIndex, xub_StrLen nLen ) const;
255 :
256 : xub_StrLen Match( const UniString& rStr ) const;
257 :
258 : xub_StrLen Search( sal_Unicode c, xub_StrLen nIndex = 0 ) const;
259 : xub_StrLen Search( const UniString& rStr, xub_StrLen nIndex = 0 ) const;
260 : xub_StrLen Search( const sal_Unicode* pCharStr, xub_StrLen nIndex = 0 ) const;
261 : xub_StrLen SearchAscii( const sal_Char* pAsciiStr, xub_StrLen nIndex = 0 ) const;
262 : xub_StrLen SearchBackward( sal_Unicode c, xub_StrLen nIndex = STRING_LEN ) const;
263 : xub_StrLen SearchChar( const sal_Unicode* pChars, xub_StrLen nIndex = 0 ) const;
264 :
265 : xub_StrLen SearchAndReplace( sal_Unicode c, sal_Unicode cRep,
266 : xub_StrLen nIndex = 0 );
267 : xub_StrLen SearchAndReplace( const UniString& rStr, const UniString& rRepStr,
268 : xub_StrLen nIndex = 0 );
269 : xub_StrLen SearchAndReplaceAscii( const sal_Char* pAsciiStr, const UniString& rRepStr,
270 : xub_StrLen nIndex = 0 );
271 : void SearchAndReplaceAll( sal_Unicode c, sal_Unicode cRep );
272 : void SearchAndReplaceAll( const UniString& rStr, const UniString& rRepStr );
273 : void SearchAndReplaceAllAscii( const sal_Char* pAsciiStr, const UniString& rRepStr );
274 :
275 : void SetToken( xub_StrLen nToken, sal_Unicode cTok, const UniString& rStr,
276 : xub_StrLen nIndex = 0 );
277 : UniString GetToken( xub_StrLen nToken, sal_Unicode cTok, sal_Int32& rIndex ) const;
278 : UniString GetToken( xub_StrLen nToken, sal_Unicode cTok = ';' ) const;
279 :
280 617898 : const sal_Unicode* GetBuffer() const { return mpData->maStr; }
281 : sal_Unicode* GetBufferAccess();
282 : void ReleaseBufferAccess( xub_StrLen nLen = STRING_LEN );
283 : sal_Unicode* AllocBuffer( xub_StrLen nLen );
284 :
285 17822700 : friend sal_Bool operator == ( const UniString& rStr1, const UniString& rStr2 )
286 17822700 : { return rStr1.Equals( rStr2 ); }
287 1497508 : friend sal_Bool operator != ( const UniString& rStr1, const UniString& rStr2 )
288 1497508 : { return !(operator == ( rStr1, rStr2 )); }
289 68053 : friend sal_Bool operator < ( const UniString& rStr1, const UniString& rStr2 )
290 68053 : { return (rStr1.CompareTo( rStr2 ) == COMPARE_LESS); }
291 0 : friend sal_Bool operator > ( const UniString& rStr1, const UniString& rStr2 )
292 0 : { return (rStr1.CompareTo( rStr2 ) == COMPARE_GREATER); }
293 : friend sal_Bool operator <= ( const UniString& rStr1, const UniString& rStr2 )
294 : { return !(operator > ( rStr1, rStr2 )); }
295 : friend sal_Bool operator >= ( const UniString& rStr1, const UniString& rStr2 )
296 : { return !(operator < ( rStr1, rStr2 )); }
297 : };
298 :
299 161647 : inline UniString UniString::Copy( xub_StrLen nIndex, xub_StrLen nCount ) const
300 : {
301 161647 : return UniString( *this, nIndex, nCount );
302 : }
303 :
304 36441 : inline UniString UniString::GetToken( xub_StrLen nToken, sal_Unicode cTok ) const
305 : {
306 36441 : sal_Int32 nTempPos = 0;
307 36441 : return GetToken( nToken, cTok, nTempPos );
308 : }
309 :
310 : template< typename charT, typename traits > std::basic_ostream<charT, traits> &
311 : operator <<(
312 : std::basic_ostream<charT, traits> & stream, UniString const & string)
313 : {
314 : return stream <<
315 : OUStringToOString(string, RTL_TEXTENCODING_UTF8).getStr();
316 : // best effort; potentially loses data due to conversion failures
317 : // (stray surrogate halves) and embedded null characters
318 : }
319 :
320 : #ifdef RTL_FAST_STRING
321 : namespace rtl
322 : {
323 : template<>
324 : struct ToStringHelper< UniString >
325 : {
326 2545 : static int length( const UniString& s ) { return s.Len(); }
327 2545 : static sal_Unicode* addData( sal_Unicode* buffer, const UniString& s ) { return addDataHelper( buffer, s.GetBuffer(), s.Len()); }
328 : static const bool allowOStringConcat = false;
329 : static const bool allowOUStringConcat = true;
330 : };
331 : }
332 :
333 : #endif
334 :
335 : // some compare operators, so that conversions from String to OUString don't
336 : // have to insert conversions all over the place
337 37 : inline bool operator==(UniString const& rLeft, OUString const& rRight)
338 : {
339 37 : return OUString(rLeft) == rRight;
340 : }
341 :
342 4490 : inline bool operator==(OUString const& rLeft, UniString const& rRight)
343 : {
344 4490 : return rLeft == OUString(rRight);
345 : }
346 :
347 2050 : inline bool operator!=(UniString const& rLeft, OUString const& rRight)
348 : {
349 2050 : return OUString(rLeft) != rRight;
350 : }
351 :
352 2196 : inline bool operator!=(OUString const& rLeft, UniString const& rRight)
353 : {
354 2196 : return rLeft != OUString(rRight);
355 : }
356 :
357 : #ifdef RTL_FAST_STRING
358 : // The above operators make comparisons involving fast string concatenation ambiguous, so provide explicit overloads.
359 : template< typename T1, typename T2 >
360 0 : inline bool operator==( const rtl::OUStringConcat< T1, T2 >& concat, const OUString& str )
361 : {
362 0 : return OUString( concat ) == str;
363 : }
364 :
365 : template< typename T1, typename T2 >
366 : inline bool operator!=( const rtl::OUStringConcat< T1, T2 >& concat, const OUString& str )
367 : {
368 : return OUString( concat ) == str;
369 : }
370 :
371 : template< typename T1, typename T2 >
372 : inline bool operator==( const OUString& str, const rtl::OUStringConcat< T1, T2 >& concat )
373 : {
374 : return str == OUString( concat );
375 : }
376 :
377 : template< typename T1, typename T2 >
378 : inline bool operator!=( const OUString& str, const rtl::OUStringConcat< T1, T2 >& concat )
379 : {
380 : return str != OUString( concat );
381 : }
382 :
383 : template< typename T1, typename T2 >
384 : inline bool operator==( const rtl::OUStringConcat< T1, T2 >& concat, const UniString& str )
385 : {
386 : return UniString( concat ) == str;
387 : }
388 :
389 : template< typename T1, typename T2 >
390 : inline bool operator!=( const rtl::OUStringConcat< T1, T2 >& concat, const UniString& str )
391 : {
392 : return UniString( concat ) == str;
393 : }
394 :
395 : template< typename T1, typename T2 >
396 : inline bool operator==( const UniString& str, const rtl::OUStringConcat< T1, T2 >& concat )
397 : {
398 : return str == UniString( concat );
399 : }
400 :
401 : template< typename T1, typename T2 >
402 : inline bool operator!=( const UniString& str, const rtl::OUStringConcat< T1, T2 >& concat )
403 : {
404 : return str != UniString( concat );
405 : }
406 :
407 : #endif
408 :
409 : #endif
410 :
411 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|