diff --git a/string/public/nsPromiseConcatenation.h b/string/public/nsPromiseConcatenation.h deleted file mode 100644 index 3339087112f8..000000000000 --- a/string/public/nsPromiseConcatenation.h +++ /dev/null @@ -1,269 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -/* nsPromiseConcatenation.h --- string concatenation machinery lives here, but don't include this file - directly, always get it by including either "nsAString.h" or one of the compatibility headers */ - -#ifndef nsPromiseConcatenation_h___ -#define nsPromiseConcatenation_h___ - - /** - NOT FOR USE BY HUMANS - - Instances of this class only exist as anonymous temporary results from |operator+()|. - This is the machinery that makes string concatenation efficient. No allocations or - character copies are required unless and until a final assignment is made. It works - its magic by overriding and forwarding calls to |GetReadableFragment()|. - - Note: |nsPromiseConcatenation| imposes some limits on string concatenation with |operator+()|. - - no more than 33 strings, e.g., |s1 + s2 + s3 + ... s32 + s33| - - left to right evaluation is required ... do not use parentheses to override this - - In practice, neither of these is onerous. Parentheses do not change the semantics of the - concatenation, only the order in which the result is assembled ... so there's no reason - for a user to need to control it. Too many strings summed together can easily be worked - around with an intermediate assignment. I wouldn't have the parentheses limitation if I - assigned the identifier mask starting at the top, the first time anybody called - |GetReadableFragment()|. - */ - -class NS_COM nsPromiseConcatenation - : public nsAPromiseString - { - public: - typedef nsPromiseConcatenation self_type; - typedef PRUnichar char_type; - typedef nsAString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const char_type* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual char_type* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - enum { kLeftString, kRightString }; - - int - GetCurrentStringFromFragment( const nsReadableFragment& aFragment ) const - { - return (NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & mFragmentIdentifierMask) ? kRightString : kLeftString; - } - - int - SetLeftStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & ~mFragmentIdentifierMask); - return kLeftString; - } - - int - SetRightStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) | mFragmentIdentifierMask); - return kRightString; - } - - public: - nsPromiseConcatenation( const string_type& aLeftString, const string_type& aRightString, PRUint32 aMask = 1 ) - : mFragmentIdentifierMask(aMask) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - nsPromiseConcatenation( const self_type& aLeftString, const string_type& aRightString ) - : mFragmentIdentifierMask(aLeftString.mFragmentIdentifierMask<<1) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - // nsPromiseConcatenation( const self_type& ); // auto-generated copy-constructor should be OK - // ~nsPromiseConcatenation(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const self_type& ); // we're immutable, you can't assign into a concatenation - - public: - - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& ) const; -// virtual PRBool PromisesExactly( const string_type& ) const; - -// const self_type operator+( const string_type& rhs ) const; - - PRUint32 GetFragmentIdentifierMask() const { return mFragmentIdentifierMask; } - - private: - void operator+( const self_type& ); // NOT TO BE IMPLEMENTED - // making this |private| stops you from over parenthesizing concatenation expressions, e.g., |(A+B) + (C+D)| - // which would break the algorithm for distributing bits in the fragment identifier - - private: - const string_type* mStrings[2]; - PRUint32 mFragmentIdentifierMask; - }; - -class NS_COM nsPromiseCConcatenation - : public nsAPromiseCString - { - public: - typedef nsPromiseCConcatenation self_type; - typedef char char_type; - typedef nsACString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const char_type* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual char_type* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - enum { kLeftString, kRightString }; - - int - GetCurrentStringFromFragment( const nsReadableFragment& aFragment ) const - { - return (NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & mFragmentIdentifierMask) ? kRightString : kLeftString; - } - - int - SetLeftStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & ~mFragmentIdentifierMask); - return kLeftString; - } - - int - SetRightStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) | mFragmentIdentifierMask); - return kRightString; - } - - public: - nsPromiseCConcatenation( const string_type& aLeftString, const string_type& aRightString, PRUint32 aMask = 1 ) - : mFragmentIdentifierMask(aMask) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - nsPromiseCConcatenation( const self_type& aLeftString, const string_type& aRightString ) - : mFragmentIdentifierMask(aLeftString.mFragmentIdentifierMask<<1) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - // nsPromiseCConcatenation( const self_type& ); // auto-generated copy-constructor should be OK - // ~nsPromiseCConcatenation(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const self_type& ); // we're immutable, you can't assign into a concatenation - - public: - - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& ) const; -// virtual PRBool PromisesExactly( const string_type& ) const; - -// const self_type operator+( const string_type& rhs ) const; - - PRUint32 GetFragmentIdentifierMask() const { return mFragmentIdentifierMask; } - - private: - void operator+( const self_type& ); // NOT TO BE IMPLEMENTED - // making this |private| stops you from over parenthesizing concatenation expressions, e.g., |(A+B) + (C+D)| - // which would break the algorithm for distributing bits in the fragment identifier - - private: - const string_type* mStrings[2]; - PRUint32 mFragmentIdentifierMask; - }; - - /* - How shall we provide |operator+()|? - - What would it return? It has to return a stack based object, because the client will - not be given an opportunity to handle memory management in an expression like - - myWritableString = stringA + stringB + stringC; - - ...so the `obvious' answer of returning a new |nsSharedString| is no good. We could - return an |nsString|, if that name were in scope here, though there's no telling what the client - will really want to do with the result. What might be better, though, - is to return a `promise' to concatenate some strings... - - By making |nsPromiseConcatenation| inherit from readable strings, we automatically handle - assignment and other interesting uses within writable strings, plus we drastically reduce - the number of cases we have to write |operator+()| for. The cost is extra temporary concat strings - in the evaluation of strings of '+'s, e.g., |A + B + C + D|, and that we have to do some work - to implement the virtual functions of readables. - */ - -inline -const nsPromiseConcatenation -operator+( const nsPromiseConcatenation& lhs, const nsAString& rhs ) - { - return nsPromiseConcatenation(lhs, rhs, lhs.GetFragmentIdentifierMask()<<1); - } - -inline -const nsPromiseCConcatenation -operator+( const nsPromiseCConcatenation& lhs, const nsACString& rhs ) - { - return nsPromiseCConcatenation(lhs, rhs, lhs.GetFragmentIdentifierMask()<<1); - } - -inline -const nsPromiseConcatenation -operator+( const nsAString& lhs, const nsAString& rhs ) - { - return nsPromiseConcatenation(lhs, rhs); - } - -inline -const nsPromiseCConcatenation -operator+( const nsACString& lhs, const nsACString& rhs ) - { - return nsPromiseCConcatenation(lhs, rhs); - } - -#if 0 -inline -const nsPromiseConcatenation -nsPromiseConcatenation::operator+( const string_type& rhs ) const - { - return nsPromiseConcatenation(*this, rhs, mFragmentIdentifierMask<<1); - } - -inline -const nsPromiseCConcatenation -nsPromiseCConcatenation::operator+( const string_type& rhs ) const - { - return nsPromiseCConcatenation(*this, rhs, mFragmentIdentifierMask<<1); - } -#endif - - -#endif /* !defined(nsPromiseConcatenation_h___) */ diff --git a/string/public/nsPromiseSubstring.h b/string/public/nsPromiseSubstring.h deleted file mode 100644 index afbe0890f598..000000000000 --- a/string/public/nsPromiseSubstring.h +++ /dev/null @@ -1,182 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -#ifndef nsPromiseSubstring_h___ -#define nsPromiseSubstring_h___ - -#ifndef nsAString_h___ -#include "nsAString.h" -#endif - -#ifndef nsStringTraits_h___ -#include "nsStringTraits.h" -#endif - - - - // - // nsPromiseSubstring - // - -class NS_COM nsPromiseSubstring - : public nsAPromiseString - /* - NOT FOR USE BY HUMANS (mostly) - - ...not unlike |nsPromiseConcatenation|. Instances of this class exist only as anonymous - temporary results from |Substring()|. Like |nsPromiseConcatenation|, this class only - holds a pointer, no string data of its own. It does its magic by overriding and forwarding - calls to |GetReadableFragment()|. - */ - { - typedef nsAString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const PRUnichar* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual PRUnichar* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - public: - nsPromiseSubstring( const string_type& aString, PRUint32 aStartPos, PRUint32 aLength ) - : mString(aString), - mStartPos( NS_MIN(aStartPos, aString.Length()) ), - mLength( NS_MIN(aLength, aString.Length()-mStartPos) ) - { - // nothing else to do here - } - - nsPromiseSubstring( const const_iterator& aStart, const const_iterator& aEnd ) - : mString(aStart.string()) - { - const_iterator zeroPoint; - mString.BeginReading(zeroPoint); - mStartPos = Distance(zeroPoint, aStart); - mLength = Distance(aStart, aEnd); - } - - // nsPromiseSubstring( const nsPromiseSubstring& ); // auto-generated copy-constructor should be OK - // ~nsPromiseSubstring(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const nsPromiseSubstring& ); // we're immutable, you can't assign into a substring - - public: - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& aString ) const { return mString.Promises(aString); } - - private: - const string_type& mString; - PRUint32 mStartPos; - PRUint32 mLength; - }; - -class NS_COM nsPromiseCSubstring - : public nsAPromiseCString - /* - NOT FOR USE BY HUMANS (mostly) - - ...not unlike |nsPromiseConcatenation|. Instances of this class exist only as anonymous - temporary results from |Substring()|. Like |nsPromiseConcatenation|, this class only - holds a pointer, no string data of its own. It does its magic by overriding and forwarding - calls to |GetReadableFragment()|. - */ - { - typedef nsACString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const char* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual char* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - public: - nsPromiseCSubstring( const string_type& aString, PRUint32 aStartPos, PRUint32 aLength ) - : mString(aString), - mStartPos( NS_MIN(aStartPos, aString.Length()) ), - mLength( NS_MIN(aLength, aString.Length()-mStartPos) ) - { - // nothing else to do here - } - - nsPromiseCSubstring( const const_iterator& aStart, const const_iterator& aEnd ) - : mString(aStart.string()) - { - const_iterator zeroPoint; - mString.BeginReading(zeroPoint); - mStartPos = Distance(zeroPoint, aStart); - mLength = Distance(aStart, aEnd); - } - - // nsPromiseCSubstring( const nsPromiseCSubstring& ); // auto-generated copy-constructor should be OK - // ~nsPromiseCSubstring(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const nsPromiseCSubstring& ); // we're immutable, you can't assign into a substring - - public: - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& aString ) const { return mString.Promises(aString); } - - private: - const string_type& mString; - PRUint32 mStartPos; - PRUint32 mLength; - }; - - - - - - - -inline -const nsPromiseCSubstring -Substring( const nsACString& aString, PRUint32 aStartPos, PRUint32 aSubstringLength ) - { - return nsPromiseCSubstring(aString, aStartPos, aSubstringLength); - } - -inline -const nsPromiseSubstring -Substring( const nsAString& aString, PRUint32 aStartPos, PRUint32 aSubstringLength ) - { - return nsPromiseSubstring(aString, aStartPos, aSubstringLength); - } - -inline -const nsPromiseCSubstring -Substring( const nsReadingIterator& aStart, const nsReadingIterator& aEnd ) - { - return nsPromiseCSubstring(aStart, aEnd); - } - -inline -const nsPromiseSubstring -Substring( const nsReadingIterator& aStart, const nsReadingIterator& aEnd ) - { - return nsPromiseSubstring(aStart, aEnd); - } - - -#endif /* !defined(nsPromiseSubstring_h___) */ diff --git a/string/src/nsPromiseConcatenation.cpp b/string/src/nsPromiseConcatenation.cpp deleted file mode 100644 index ed1bd50b6c7a..000000000000 --- a/string/src/nsPromiseConcatenation.cpp +++ /dev/null @@ -1,197 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -//-------1---------2---------3---------4---------5---------6---------7---------8 - -#include "nsAString.h" - // remember, no one should include "nsPromiseConcatenation.h" themselves - // one always gets it through "nsAString.h" - -PRUint32 -nsPromiseConcatenation::Length() const - { - return mStrings[kLeftString]->Length() + mStrings[kRightString]->Length(); - } - -PRBool -nsPromiseConcatenation::Promises( const string_type& aString ) const - { - return mStrings[0]->Promises(aString) || mStrings[1]->Promises(aString); - } - -#if 0 -PRBool -nsPromiseConcatenation::PromisesExactly( const string_type& aString ) const - { - // Not really like this, test for the empty string, etc - return mStrings[0] == &aString && !mStrings[1] || !mStrings[0] && mStrings[1] == &aString; - } -#endif - -const PRUnichar* -nsPromiseConcatenation::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - int whichString; - - // based on the request, pick which string we will forward the |GetReadableFragment()| call into - - switch ( aRequest ) - { - case kPrevFragment: - case kNextFragment: - whichString = GetCurrentStringFromFragment(aFragment); - break; - - case kFirstFragment: - whichString = SetLeftStringInFragment(aFragment); - break; - - case kLastFragment: - whichString = SetRightStringInFragment(aFragment); - break; - - case kFragmentAt: - PRUint32 leftLength = mStrings[kLeftString]->Length(); - if ( aPosition < leftLength ) - whichString = SetLeftStringInFragment(aFragment); - else - { - whichString = SetRightStringInFragment(aFragment); - aPosition -= leftLength; - } - break; - - } - - const char_type* result; - PRBool done; - do - { - done = PR_TRUE; - result = mStrings[whichString]->GetReadableFragment(aFragment, aRequest, aPosition); - - if ( !result ) - { - done = PR_FALSE; - if ( aRequest == kNextFragment && whichString == kLeftString ) - { - aRequest = kFirstFragment; - whichString = SetRightStringInFragment(aFragment); - } - else if ( aRequest == kPrevFragment && whichString == kRightString ) - { - aRequest = kLastFragment; - whichString = SetLeftStringInFragment(aFragment); - } - else - done = PR_TRUE; - } - } - while ( !done ); - return result; - } - - -PRUint32 -nsPromiseCConcatenation::Length() const - { - return mStrings[kLeftString]->Length() + mStrings[kRightString]->Length(); - } - -PRBool -nsPromiseCConcatenation::Promises( const string_type& aString ) const - { - return mStrings[0]->Promises(aString) || mStrings[1]->Promises(aString); - } - -#if 0 -PRBool -nsPromiseCConcatenation::PromisesExactly( const string_type& aString ) const - { - // Not really like this, test for the empty string, etc - return mStrings[0] == &aString && !mStrings[1] || !mStrings[0] && mStrings[1] == &aString; - } -#endif - -const char* -nsPromiseCConcatenation::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - int whichString; - - // based on the request, pick which string we will forward the |GetReadableFragment()| call into - - switch ( aRequest ) - { - case kPrevFragment: - case kNextFragment: - whichString = GetCurrentStringFromFragment(aFragment); - break; - - case kFirstFragment: - whichString = SetLeftStringInFragment(aFragment); - break; - - case kLastFragment: - whichString = SetRightStringInFragment(aFragment); - break; - - case kFragmentAt: - PRUint32 leftLength = mStrings[kLeftString]->Length(); - if ( aPosition < leftLength ) - whichString = SetLeftStringInFragment(aFragment); - else - { - whichString = SetRightStringInFragment(aFragment); - aPosition -= leftLength; - } - break; - - } - - const char_type* result; - PRBool done; - do - { - done = PR_TRUE; - result = mStrings[whichString]->GetReadableFragment(aFragment, aRequest, aPosition); - - if ( !result ) - { - done = PR_FALSE; - if ( aRequest == kNextFragment && whichString == kLeftString ) - { - aRequest = kFirstFragment; - whichString = SetRightStringInFragment(aFragment); - } - else if ( aRequest == kPrevFragment && whichString == kRightString ) - { - aRequest = kLastFragment; - whichString = SetLeftStringInFragment(aFragment); - } - else - done = PR_TRUE; - } - } - while ( !done ); - return result; - } diff --git a/string/src/nsPromiseSubstring.cpp b/string/src/nsPromiseSubstring.cpp deleted file mode 100644 index 563cd3b48d4a..000000000000 --- a/string/src/nsPromiseSubstring.cpp +++ /dev/null @@ -1,123 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -#include "nsPromiseSubstring.h" - -PRUint32 -nsPromiseSubstring::Length() const - { - return mLength; - } - -const PRUnichar* -nsPromiseSubstring::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - // Offset any request for a specific position (First, Last, At) by our - // substrings startpos within the owning string - - if ( aRequest == kFirstFragment ) - { - aPosition = mStartPos; - aRequest = kFragmentAt; - } - else if ( aRequest == kLastFragment ) - { - aPosition = mStartPos + mLength; - aRequest = kFragmentAt; - } - else if ( aRequest == kFragmentAt ) - aPosition += mStartPos; - - // requests for |kNextFragment| or |kPrevFragment| are just relayed down into the string we're slicing - - const PRUnichar* position_ptr = mString.GetReadableFragment(aFragment, aRequest, aPosition); - - // If |GetReadableFragment| returns |0|, then we are off the string, the contents of the - // fragment are garbage. - - // Therefore, only need to fix up the fragment boundaries when |position_ptr| is not null - if ( position_ptr ) - { - // if there's more physical data in the returned fragment than I logically have left... - size_t logical_size_backward = aPosition - mStartPos; - if ( size_t(position_ptr - aFragment.mStart) > logical_size_backward ) - aFragment.mStart = position_ptr - logical_size_backward; - - size_t logical_size_forward = mLength - logical_size_backward; - if ( size_t(aFragment.mEnd - position_ptr) > logical_size_forward ) - aFragment.mEnd = position_ptr + logical_size_forward; - } - - return position_ptr; - } - - - - -PRUint32 -nsPromiseCSubstring::Length() const - { - return mLength; - } - -const char* -nsPromiseCSubstring::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - // Offset any request for a specific position (First, Last, At) by our - // substrings startpos within the owning string - - if ( aRequest == kFirstFragment ) - { - aPosition = mStartPos; - aRequest = kFragmentAt; - } - else if ( aRequest == kLastFragment ) - { - aPosition = mStartPos + mLength; - aRequest = kFragmentAt; - } - else if ( aRequest == kFragmentAt ) - aPosition += mStartPos; - - // requests for |kNextFragment| or |kPrevFragment| are just relayed down into the string we're slicing - - const char* position_ptr = mString.GetReadableFragment(aFragment, aRequest, aPosition); - - // If |GetReadableFragment| returns |0|, then we are off the string, the contents of the - // fragment are garbage. - - // Therefore, only need to fix up the fragment boundaries when |position_ptr| is not null - if ( position_ptr ) - { - // if there's more physical data in the returned fragment than I logically have left... - size_t logical_size_backward = aPosition - mStartPos; - if ( size_t(position_ptr - aFragment.mStart) > logical_size_backward ) - aFragment.mStart = position_ptr - logical_size_backward; - - size_t logical_size_forward = mLength - logical_size_backward; - if ( size_t(aFragment.mEnd - position_ptr) > logical_size_forward ) - aFragment.mEnd = position_ptr + logical_size_forward; - } - - return position_ptr; - } diff --git a/xpcom/string/public/nsPromiseConcatenation.h b/xpcom/string/public/nsPromiseConcatenation.h deleted file mode 100644 index 3339087112f8..000000000000 --- a/xpcom/string/public/nsPromiseConcatenation.h +++ /dev/null @@ -1,269 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -/* nsPromiseConcatenation.h --- string concatenation machinery lives here, but don't include this file - directly, always get it by including either "nsAString.h" or one of the compatibility headers */ - -#ifndef nsPromiseConcatenation_h___ -#define nsPromiseConcatenation_h___ - - /** - NOT FOR USE BY HUMANS - - Instances of this class only exist as anonymous temporary results from |operator+()|. - This is the machinery that makes string concatenation efficient. No allocations or - character copies are required unless and until a final assignment is made. It works - its magic by overriding and forwarding calls to |GetReadableFragment()|. - - Note: |nsPromiseConcatenation| imposes some limits on string concatenation with |operator+()|. - - no more than 33 strings, e.g., |s1 + s2 + s3 + ... s32 + s33| - - left to right evaluation is required ... do not use parentheses to override this - - In practice, neither of these is onerous. Parentheses do not change the semantics of the - concatenation, only the order in which the result is assembled ... so there's no reason - for a user to need to control it. Too many strings summed together can easily be worked - around with an intermediate assignment. I wouldn't have the parentheses limitation if I - assigned the identifier mask starting at the top, the first time anybody called - |GetReadableFragment()|. - */ - -class NS_COM nsPromiseConcatenation - : public nsAPromiseString - { - public: - typedef nsPromiseConcatenation self_type; - typedef PRUnichar char_type; - typedef nsAString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const char_type* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual char_type* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - enum { kLeftString, kRightString }; - - int - GetCurrentStringFromFragment( const nsReadableFragment& aFragment ) const - { - return (NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & mFragmentIdentifierMask) ? kRightString : kLeftString; - } - - int - SetLeftStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & ~mFragmentIdentifierMask); - return kLeftString; - } - - int - SetRightStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) | mFragmentIdentifierMask); - return kRightString; - } - - public: - nsPromiseConcatenation( const string_type& aLeftString, const string_type& aRightString, PRUint32 aMask = 1 ) - : mFragmentIdentifierMask(aMask) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - nsPromiseConcatenation( const self_type& aLeftString, const string_type& aRightString ) - : mFragmentIdentifierMask(aLeftString.mFragmentIdentifierMask<<1) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - // nsPromiseConcatenation( const self_type& ); // auto-generated copy-constructor should be OK - // ~nsPromiseConcatenation(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const self_type& ); // we're immutable, you can't assign into a concatenation - - public: - - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& ) const; -// virtual PRBool PromisesExactly( const string_type& ) const; - -// const self_type operator+( const string_type& rhs ) const; - - PRUint32 GetFragmentIdentifierMask() const { return mFragmentIdentifierMask; } - - private: - void operator+( const self_type& ); // NOT TO BE IMPLEMENTED - // making this |private| stops you from over parenthesizing concatenation expressions, e.g., |(A+B) + (C+D)| - // which would break the algorithm for distributing bits in the fragment identifier - - private: - const string_type* mStrings[2]; - PRUint32 mFragmentIdentifierMask; - }; - -class NS_COM nsPromiseCConcatenation - : public nsAPromiseCString - { - public: - typedef nsPromiseCConcatenation self_type; - typedef char char_type; - typedef nsACString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const char_type* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual char_type* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - enum { kLeftString, kRightString }; - - int - GetCurrentStringFromFragment( const nsReadableFragment& aFragment ) const - { - return (NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & mFragmentIdentifierMask) ? kRightString : kLeftString; - } - - int - SetLeftStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) & ~mFragmentIdentifierMask); - return kLeftString; - } - - int - SetRightStringInFragment( nsReadableFragment& aFragment ) const - { - aFragment.mFragmentIdentifier = NS_REINTERPRET_CAST(void*, NS_REINTERPRET_CAST(PRUint32, aFragment.mFragmentIdentifier) | mFragmentIdentifierMask); - return kRightString; - } - - public: - nsPromiseCConcatenation( const string_type& aLeftString, const string_type& aRightString, PRUint32 aMask = 1 ) - : mFragmentIdentifierMask(aMask) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - nsPromiseCConcatenation( const self_type& aLeftString, const string_type& aRightString ) - : mFragmentIdentifierMask(aLeftString.mFragmentIdentifierMask<<1) - { - mStrings[kLeftString] = &aLeftString; - mStrings[kRightString] = &aRightString; - } - - // nsPromiseCConcatenation( const self_type& ); // auto-generated copy-constructor should be OK - // ~nsPromiseCConcatenation(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const self_type& ); // we're immutable, you can't assign into a concatenation - - public: - - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& ) const; -// virtual PRBool PromisesExactly( const string_type& ) const; - -// const self_type operator+( const string_type& rhs ) const; - - PRUint32 GetFragmentIdentifierMask() const { return mFragmentIdentifierMask; } - - private: - void operator+( const self_type& ); // NOT TO BE IMPLEMENTED - // making this |private| stops you from over parenthesizing concatenation expressions, e.g., |(A+B) + (C+D)| - // which would break the algorithm for distributing bits in the fragment identifier - - private: - const string_type* mStrings[2]; - PRUint32 mFragmentIdentifierMask; - }; - - /* - How shall we provide |operator+()|? - - What would it return? It has to return a stack based object, because the client will - not be given an opportunity to handle memory management in an expression like - - myWritableString = stringA + stringB + stringC; - - ...so the `obvious' answer of returning a new |nsSharedString| is no good. We could - return an |nsString|, if that name were in scope here, though there's no telling what the client - will really want to do with the result. What might be better, though, - is to return a `promise' to concatenate some strings... - - By making |nsPromiseConcatenation| inherit from readable strings, we automatically handle - assignment and other interesting uses within writable strings, plus we drastically reduce - the number of cases we have to write |operator+()| for. The cost is extra temporary concat strings - in the evaluation of strings of '+'s, e.g., |A + B + C + D|, and that we have to do some work - to implement the virtual functions of readables. - */ - -inline -const nsPromiseConcatenation -operator+( const nsPromiseConcatenation& lhs, const nsAString& rhs ) - { - return nsPromiseConcatenation(lhs, rhs, lhs.GetFragmentIdentifierMask()<<1); - } - -inline -const nsPromiseCConcatenation -operator+( const nsPromiseCConcatenation& lhs, const nsACString& rhs ) - { - return nsPromiseCConcatenation(lhs, rhs, lhs.GetFragmentIdentifierMask()<<1); - } - -inline -const nsPromiseConcatenation -operator+( const nsAString& lhs, const nsAString& rhs ) - { - return nsPromiseConcatenation(lhs, rhs); - } - -inline -const nsPromiseCConcatenation -operator+( const nsACString& lhs, const nsACString& rhs ) - { - return nsPromiseCConcatenation(lhs, rhs); - } - -#if 0 -inline -const nsPromiseConcatenation -nsPromiseConcatenation::operator+( const string_type& rhs ) const - { - return nsPromiseConcatenation(*this, rhs, mFragmentIdentifierMask<<1); - } - -inline -const nsPromiseCConcatenation -nsPromiseCConcatenation::operator+( const string_type& rhs ) const - { - return nsPromiseCConcatenation(*this, rhs, mFragmentIdentifierMask<<1); - } -#endif - - -#endif /* !defined(nsPromiseConcatenation_h___) */ diff --git a/xpcom/string/public/nsPromiseSubstring.h b/xpcom/string/public/nsPromiseSubstring.h deleted file mode 100644 index afbe0890f598..000000000000 --- a/xpcom/string/public/nsPromiseSubstring.h +++ /dev/null @@ -1,182 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -#ifndef nsPromiseSubstring_h___ -#define nsPromiseSubstring_h___ - -#ifndef nsAString_h___ -#include "nsAString.h" -#endif - -#ifndef nsStringTraits_h___ -#include "nsStringTraits.h" -#endif - - - - // - // nsPromiseSubstring - // - -class NS_COM nsPromiseSubstring - : public nsAPromiseString - /* - NOT FOR USE BY HUMANS (mostly) - - ...not unlike |nsPromiseConcatenation|. Instances of this class exist only as anonymous - temporary results from |Substring()|. Like |nsPromiseConcatenation|, this class only - holds a pointer, no string data of its own. It does its magic by overriding and forwarding - calls to |GetReadableFragment()|. - */ - { - typedef nsAString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const PRUnichar* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual PRUnichar* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - public: - nsPromiseSubstring( const string_type& aString, PRUint32 aStartPos, PRUint32 aLength ) - : mString(aString), - mStartPos( NS_MIN(aStartPos, aString.Length()) ), - mLength( NS_MIN(aLength, aString.Length()-mStartPos) ) - { - // nothing else to do here - } - - nsPromiseSubstring( const const_iterator& aStart, const const_iterator& aEnd ) - : mString(aStart.string()) - { - const_iterator zeroPoint; - mString.BeginReading(zeroPoint); - mStartPos = Distance(zeroPoint, aStart); - mLength = Distance(aStart, aEnd); - } - - // nsPromiseSubstring( const nsPromiseSubstring& ); // auto-generated copy-constructor should be OK - // ~nsPromiseSubstring(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const nsPromiseSubstring& ); // we're immutable, you can't assign into a substring - - public: - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& aString ) const { return mString.Promises(aString); } - - private: - const string_type& mString; - PRUint32 mStartPos; - PRUint32 mLength; - }; - -class NS_COM nsPromiseCSubstring - : public nsAPromiseCString - /* - NOT FOR USE BY HUMANS (mostly) - - ...not unlike |nsPromiseConcatenation|. Instances of this class exist only as anonymous - temporary results from |Substring()|. Like |nsPromiseConcatenation|, this class only - holds a pointer, no string data of its own. It does its magic by overriding and forwarding - calls to |GetReadableFragment()|. - */ - { - typedef nsACString string_type; - typedef string_type::const_iterator const_iterator; - - protected: - virtual const char* GetReadableFragment( nsReadableFragment&, nsFragmentRequest, PRUint32 ) const; - virtual char* GetWritableFragment( nsWritableFragment&, nsFragmentRequest, PRUint32 ) { return 0; } - - public: - nsPromiseCSubstring( const string_type& aString, PRUint32 aStartPos, PRUint32 aLength ) - : mString(aString), - mStartPos( NS_MIN(aStartPos, aString.Length()) ), - mLength( NS_MIN(aLength, aString.Length()-mStartPos) ) - { - // nothing else to do here - } - - nsPromiseCSubstring( const const_iterator& aStart, const const_iterator& aEnd ) - : mString(aStart.string()) - { - const_iterator zeroPoint; - mString.BeginReading(zeroPoint); - mStartPos = Distance(zeroPoint, aStart); - mLength = Distance(aStart, aEnd); - } - - // nsPromiseCSubstring( const nsPromiseCSubstring& ); // auto-generated copy-constructor should be OK - // ~nsPromiseCSubstring(); // auto-generated destructor OK - - private: - // NOT TO BE IMPLEMENTED - void operator=( const nsPromiseCSubstring& ); // we're immutable, you can't assign into a substring - - public: - virtual PRUint32 Length() const; - virtual PRBool Promises( const string_type& aString ) const { return mString.Promises(aString); } - - private: - const string_type& mString; - PRUint32 mStartPos; - PRUint32 mLength; - }; - - - - - - - -inline -const nsPromiseCSubstring -Substring( const nsACString& aString, PRUint32 aStartPos, PRUint32 aSubstringLength ) - { - return nsPromiseCSubstring(aString, aStartPos, aSubstringLength); - } - -inline -const nsPromiseSubstring -Substring( const nsAString& aString, PRUint32 aStartPos, PRUint32 aSubstringLength ) - { - return nsPromiseSubstring(aString, aStartPos, aSubstringLength); - } - -inline -const nsPromiseCSubstring -Substring( const nsReadingIterator& aStart, const nsReadingIterator& aEnd ) - { - return nsPromiseCSubstring(aStart, aEnd); - } - -inline -const nsPromiseSubstring -Substring( const nsReadingIterator& aStart, const nsReadingIterator& aEnd ) - { - return nsPromiseSubstring(aStart, aEnd); - } - - -#endif /* !defined(nsPromiseSubstring_h___) */ diff --git a/xpcom/string/src/nsPromiseConcatenation.cpp b/xpcom/string/src/nsPromiseConcatenation.cpp deleted file mode 100644 index ed1bd50b6c7a..000000000000 --- a/xpcom/string/src/nsPromiseConcatenation.cpp +++ /dev/null @@ -1,197 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -//-------1---------2---------3---------4---------5---------6---------7---------8 - -#include "nsAString.h" - // remember, no one should include "nsPromiseConcatenation.h" themselves - // one always gets it through "nsAString.h" - -PRUint32 -nsPromiseConcatenation::Length() const - { - return mStrings[kLeftString]->Length() + mStrings[kRightString]->Length(); - } - -PRBool -nsPromiseConcatenation::Promises( const string_type& aString ) const - { - return mStrings[0]->Promises(aString) || mStrings[1]->Promises(aString); - } - -#if 0 -PRBool -nsPromiseConcatenation::PromisesExactly( const string_type& aString ) const - { - // Not really like this, test for the empty string, etc - return mStrings[0] == &aString && !mStrings[1] || !mStrings[0] && mStrings[1] == &aString; - } -#endif - -const PRUnichar* -nsPromiseConcatenation::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - int whichString; - - // based on the request, pick which string we will forward the |GetReadableFragment()| call into - - switch ( aRequest ) - { - case kPrevFragment: - case kNextFragment: - whichString = GetCurrentStringFromFragment(aFragment); - break; - - case kFirstFragment: - whichString = SetLeftStringInFragment(aFragment); - break; - - case kLastFragment: - whichString = SetRightStringInFragment(aFragment); - break; - - case kFragmentAt: - PRUint32 leftLength = mStrings[kLeftString]->Length(); - if ( aPosition < leftLength ) - whichString = SetLeftStringInFragment(aFragment); - else - { - whichString = SetRightStringInFragment(aFragment); - aPosition -= leftLength; - } - break; - - } - - const char_type* result; - PRBool done; - do - { - done = PR_TRUE; - result = mStrings[whichString]->GetReadableFragment(aFragment, aRequest, aPosition); - - if ( !result ) - { - done = PR_FALSE; - if ( aRequest == kNextFragment && whichString == kLeftString ) - { - aRequest = kFirstFragment; - whichString = SetRightStringInFragment(aFragment); - } - else if ( aRequest == kPrevFragment && whichString == kRightString ) - { - aRequest = kLastFragment; - whichString = SetLeftStringInFragment(aFragment); - } - else - done = PR_TRUE; - } - } - while ( !done ); - return result; - } - - -PRUint32 -nsPromiseCConcatenation::Length() const - { - return mStrings[kLeftString]->Length() + mStrings[kRightString]->Length(); - } - -PRBool -nsPromiseCConcatenation::Promises( const string_type& aString ) const - { - return mStrings[0]->Promises(aString) || mStrings[1]->Promises(aString); - } - -#if 0 -PRBool -nsPromiseCConcatenation::PromisesExactly( const string_type& aString ) const - { - // Not really like this, test for the empty string, etc - return mStrings[0] == &aString && !mStrings[1] || !mStrings[0] && mStrings[1] == &aString; - } -#endif - -const char* -nsPromiseCConcatenation::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - int whichString; - - // based on the request, pick which string we will forward the |GetReadableFragment()| call into - - switch ( aRequest ) - { - case kPrevFragment: - case kNextFragment: - whichString = GetCurrentStringFromFragment(aFragment); - break; - - case kFirstFragment: - whichString = SetLeftStringInFragment(aFragment); - break; - - case kLastFragment: - whichString = SetRightStringInFragment(aFragment); - break; - - case kFragmentAt: - PRUint32 leftLength = mStrings[kLeftString]->Length(); - if ( aPosition < leftLength ) - whichString = SetLeftStringInFragment(aFragment); - else - { - whichString = SetRightStringInFragment(aFragment); - aPosition -= leftLength; - } - break; - - } - - const char_type* result; - PRBool done; - do - { - done = PR_TRUE; - result = mStrings[whichString]->GetReadableFragment(aFragment, aRequest, aPosition); - - if ( !result ) - { - done = PR_FALSE; - if ( aRequest == kNextFragment && whichString == kLeftString ) - { - aRequest = kFirstFragment; - whichString = SetRightStringInFragment(aFragment); - } - else if ( aRequest == kPrevFragment && whichString == kRightString ) - { - aRequest = kLastFragment; - whichString = SetLeftStringInFragment(aFragment); - } - else - done = PR_TRUE; - } - } - while ( !done ); - return result; - } diff --git a/xpcom/string/src/nsPromiseSubstring.cpp b/xpcom/string/src/nsPromiseSubstring.cpp deleted file mode 100644 index 563cd3b48d4a..000000000000 --- a/xpcom/string/src/nsPromiseSubstring.cpp +++ /dev/null @@ -1,123 +0,0 @@ -/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* - * The contents of this file are subject to the Mozilla Public - * 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.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS - * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or - * implied. See the License for the specific language governing - * rights and limitations under the License. - * - * The Original Code is Mozilla. - * - * The Initial Developer of the Original Code is Netscape - * Communications. Portions created by Netscape Communications are - * Copyright (C) 2001 by Netscape Communications. All - * Rights Reserved. - * - * Contributor(s): - * Scott Collins (original author) - */ - -#include "nsPromiseSubstring.h" - -PRUint32 -nsPromiseSubstring::Length() const - { - return mLength; - } - -const PRUnichar* -nsPromiseSubstring::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - // Offset any request for a specific position (First, Last, At) by our - // substrings startpos within the owning string - - if ( aRequest == kFirstFragment ) - { - aPosition = mStartPos; - aRequest = kFragmentAt; - } - else if ( aRequest == kLastFragment ) - { - aPosition = mStartPos + mLength; - aRequest = kFragmentAt; - } - else if ( aRequest == kFragmentAt ) - aPosition += mStartPos; - - // requests for |kNextFragment| or |kPrevFragment| are just relayed down into the string we're slicing - - const PRUnichar* position_ptr = mString.GetReadableFragment(aFragment, aRequest, aPosition); - - // If |GetReadableFragment| returns |0|, then we are off the string, the contents of the - // fragment are garbage. - - // Therefore, only need to fix up the fragment boundaries when |position_ptr| is not null - if ( position_ptr ) - { - // if there's more physical data in the returned fragment than I logically have left... - size_t logical_size_backward = aPosition - mStartPos; - if ( size_t(position_ptr - aFragment.mStart) > logical_size_backward ) - aFragment.mStart = position_ptr - logical_size_backward; - - size_t logical_size_forward = mLength - logical_size_backward; - if ( size_t(aFragment.mEnd - position_ptr) > logical_size_forward ) - aFragment.mEnd = position_ptr + logical_size_forward; - } - - return position_ptr; - } - - - - -PRUint32 -nsPromiseCSubstring::Length() const - { - return mLength; - } - -const char* -nsPromiseCSubstring::GetReadableFragment( nsReadableFragment& aFragment, nsFragmentRequest aRequest, PRUint32 aPosition ) const - { - // Offset any request for a specific position (First, Last, At) by our - // substrings startpos within the owning string - - if ( aRequest == kFirstFragment ) - { - aPosition = mStartPos; - aRequest = kFragmentAt; - } - else if ( aRequest == kLastFragment ) - { - aPosition = mStartPos + mLength; - aRequest = kFragmentAt; - } - else if ( aRequest == kFragmentAt ) - aPosition += mStartPos; - - // requests for |kNextFragment| or |kPrevFragment| are just relayed down into the string we're slicing - - const char* position_ptr = mString.GetReadableFragment(aFragment, aRequest, aPosition); - - // If |GetReadableFragment| returns |0|, then we are off the string, the contents of the - // fragment are garbage. - - // Therefore, only need to fix up the fragment boundaries when |position_ptr| is not null - if ( position_ptr ) - { - // if there's more physical data in the returned fragment than I logically have left... - size_t logical_size_backward = aPosition - mStartPos; - if ( size_t(position_ptr - aFragment.mStart) > logical_size_backward ) - aFragment.mStart = position_ptr - logical_size_backward; - - size_t logical_size_forward = mLength - logical_size_backward; - if ( size_t(aFragment.mEnd - position_ptr) > logical_size_forward ) - aFragment.mEnd = position_ptr + logical_size_forward; - } - - return position_ptr; - }