X-Git-Url: http://git.buserror.net/cgi-bin/gitweb.cgi?p=polintos%2Fscott%2Fpriv.git;a=blobdiff_plain;f=include%2Fc%2B%2B%2Fstl%2Fstl%2F_string_base.h;fp=include%2Fc%2B%2B%2Fstl%2Fstl%2F_string_base.h;h=923049dccf121021702c07e420844a156835638c;hp=0000000000000000000000000000000000000000;hb=173d8903eb9d51a4ea7d7fa3e52dc86c9bb6d4f1;hpb=b024710fe2b60cd4a42a8993b61333d6cdb56ca3 diff --git a/include/c++/stl/stl/_string_base.h b/include/c++/stl/stl/_string_base.h new file mode 100644 index 0000000..923049d --- /dev/null +++ b/include/c++/stl/stl/_string_base.h @@ -0,0 +1,249 @@ +/* + * Copyright (c) 1997-1999 + * Silicon Graphics Computer Systems, Inc. + * + * Copyright (c) 1999 + * Boris Fomitchev + * + * Copyright (c) 2003 + * Francois Dumont + * + * This material is provided "as is", with absolutely no warranty expressed + * or implied. Any use is at your own risk. + * + * Permission to use or copy this software for any purpose is hereby granted + * without fee, provided the above notices are retained on all copies. + * Permission to modify the code and to distribute modified code is granted, + * provided the above notices are retained, and a notice that the code was + * modified is included with the above copyright notice. + * + */ + +#ifndef _STLP_STRING_BASE_H +#define _STLP_STRING_BASE_H + +// ------------------------------------------------------------ +// Class _String_base. + +// _String_base is a helper class that makes it it easier to write an +// exception-safe version of basic_string. The constructor allocates, +// but does not initialize, a block of memory. The destructor +// deallocates, but does not destroy elements within, a block of +// memory. The destructor assumes that _M_start either is null, or else +// points to a block of memory that was allocated using _String_base's +// allocator and whose size is _M_end_of_storage._M_data - _M_start. + +_STLP_BEGIN_NAMESPACE + +_STLP_MOVE_TO_PRIV_NAMESPACE + +#ifndef _STLP_SHORT_STRING_SZ +# define _STLP_SHORT_STRING_SZ 16 +#endif + +template +class _String_base { + typedef _String_base<_Tp, _Alloc> _Self; +protected: + _STLP_FORCE_ALLOCATORS(_Tp, _Alloc) +public: + //dums: Some compiler(MSVC6) require it to be public not simply protected! + enum {_DEFAULT_SIZE = _STLP_SHORT_STRING_SZ}; + //This is needed by the full move framework + typedef typename _Alloc_traits<_Tp, _Alloc>::allocator_type allocator_type; + typedef _STLP_alloc_proxy<_Tp*, _Tp, allocator_type> _AllocProxy; + typedef size_t size_type; +private: +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + union _Buffers { + _Tp* _M_dynamic_buf; + _Tp _M_static_buf[_DEFAULT_SIZE]; + } _M_buffers; +#else + _Tp* _M_start; +#endif /* _STLP_USE_SHORT_STRING_OPTIM */ +protected: +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + bool _M_using_static_buf() const { + return (_M_end_of_storage._M_data == _M_buffers._M_static_buf + _DEFAULT_SIZE); + } + _Tp const* _M_Start() const { + return _M_using_static_buf()?_M_buffers._M_static_buf:_M_buffers._M_dynamic_buf; + } + _Tp* _M_Start() { + return _M_using_static_buf()?_M_buffers._M_static_buf:_M_buffers._M_dynamic_buf; + } +#else + _Tp const* _M_Start() const {return _M_start;} + _Tp* _M_Start() {return _M_start;} +#endif /* _STLP_USE_SHORT_STRING_OPTIM */ + + _Tp* _M_finish; + _AllocProxy _M_end_of_storage; + + _Tp const* _M_Finish() const {return _M_finish;} + _Tp* _M_Finish() {return _M_finish;} + + // Precondition: 0 < __n <= max_size(). + void _M_allocate_block(size_t __n = _DEFAULT_SIZE); + void _M_deallocate_block() { +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + if (!_M_using_static_buf() && (_M_buffers._M_dynamic_buf != 0)) + _M_end_of_storage.deallocate(_M_buffers._M_dynamic_buf, _M_end_of_storage._M_data - _M_buffers._M_dynamic_buf); +#else + if (_M_start != 0) + _M_end_of_storage.deallocate(_M_start, _M_end_of_storage._M_data - _M_start); +#endif /* _STLP_USE_SHORT_STRING_OPTIM */ + } + + size_t max_size() const { + const size_type __string_max_size = size_type(-1) / sizeof(_Tp); + typename allocator_type::size_type __alloc_max_size = _M_end_of_storage.max_size(); + return (min)(__alloc_max_size, __string_max_size) - 1; + } + + _String_base(const allocator_type& __a) +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + : _M_finish(_M_buffers._M_static_buf), _M_end_of_storage(__a, _M_buffers._M_static_buf + _DEFAULT_SIZE) +#else + : _M_start(0), _M_finish(0), _M_end_of_storage(__a, (_Tp*)0) +#endif + {} + + _String_base(const allocator_type& __a, size_t __n) +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + : _M_finish(_M_buffers._M_static_buf), _M_end_of_storage(__a, _M_buffers._M_static_buf + _DEFAULT_SIZE) { +#else + : _M_start(0), _M_finish(0), _M_end_of_storage(__a, (_Tp*)0) { +#endif + _M_allocate_block(__n); + } + +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + void _M_move_src (_Self &src) { + if (src._M_using_static_buf()) { + _M_buffers = src._M_buffers; + _M_finish = _M_buffers._M_static_buf + (src._M_finish - src._M_buffers._M_static_buf); + _M_end_of_storage._M_data = _M_buffers._M_static_buf + _DEFAULT_SIZE; + } + else { + _M_buffers._M_dynamic_buf = src._M_buffers._M_dynamic_buf; + _M_finish = src._M_finish; + _M_end_of_storage._M_data = src._M_end_of_storage._M_data; + src._M_buffers._M_dynamic_buf = 0; + } + } +#endif + + _String_base(__move_source<_Self> src) +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + : _M_end_of_storage(__move_source<_AllocProxy>(src.get()._M_end_of_storage)) { + _M_move_src(src.get()); +#else + : _M_start(src.get()._M_start), _M_finish(src.get()._M_finish), + _M_end_of_storage(__move_source<_AllocProxy>(src.get()._M_end_of_storage)) { + src.get()._M_start = 0; +#endif + } + + ~_String_base() { _M_deallocate_block(); } + + void _M_reset(_Tp *__start, _Tp *__finish, _Tp *__end_of_storage) { +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + _M_buffers._M_dynamic_buf = __start; +#else + _M_start = __start; +#endif + _M_finish = __finish; + _M_end_of_storage._M_data = __end_of_storage; + } + + void _M_destroy_back () { +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + if (!_M_using_static_buf()) +#endif /* _STLP_USE_SHORT_STRING_OPTIM */ + _STLP_STD::_Destroy(_M_finish); + } + + void _M_destroy_range(size_t __from_off = 0, size_t __to_off = 1) { +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + if (!_M_using_static_buf()) + _STLP_STD::_Destroy_Range(_M_buffers._M_dynamic_buf + __from_off, _M_finish + __to_off); +#else + _STLP_STD::_Destroy_Range(_M_start + __from_off, _M_finish + __to_off); +#endif /* _STLP_USE_SHORT_STRING_OPTIM */ + } + + void _M_destroy_ptr_range(_Tp *__f, _Tp *__l) { +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + if (!_M_using_static_buf()) +#endif /* _STLP_USE_SHORT_STRING_OPTIM */ + _STLP_STD::_Destroy_Range(__f, __l); + } + + void _M_Swap(_Self &__s) { +#if defined (_STLP_USE_SHORT_STRING_OPTIM) + if (_M_using_static_buf()) { + if (__s._M_using_static_buf()) { + _STLP_STD::swap(_M_buffers, __s._M_buffers); + _Tp *__tmp = _M_finish; + _M_finish = _M_buffers._M_static_buf + (__s._M_finish - __s._M_buffers._M_static_buf); + __s._M_finish = __s._M_buffers._M_static_buf + (__tmp - _M_buffers._M_static_buf); + //We need to swap _M_end_of_storage for allocators with state: + _M_end_of_storage.swap(__s._M_end_of_storage); + _M_end_of_storage._M_data = _M_buffers._M_static_buf + _DEFAULT_SIZE; + __s._M_end_of_storage._M_data = __s._M_buffers._M_static_buf + _DEFAULT_SIZE; + } else { + __s._M_Swap(*this); + return; + } + } + else if (__s._M_using_static_buf()) { + _Tp *__tmp = _M_buffers._M_dynamic_buf; + _Tp *__tmp_finish = _M_finish; + _Tp *__tmp_end_data = _M_end_of_storage._M_data; + _M_buffers = __s._M_buffers; + //We need to swap _M_end_of_storage for allocators with state: + _M_end_of_storage.swap(__s._M_end_of_storage); + _M_end_of_storage._M_data = _M_buffers._M_static_buf + _DEFAULT_SIZE; + _M_finish = _M_buffers._M_static_buf + (__s._M_finish - __s._M_buffers._M_static_buf); + __s._M_buffers._M_dynamic_buf = __tmp; + __s._M_end_of_storage._M_data = __tmp_end_data; + __s._M_finish = __tmp_finish; + } + else { + _STLP_STD::swap(_M_buffers._M_dynamic_buf, __s._M_buffers._M_dynamic_buf); + _M_end_of_storage.swap(__s._M_end_of_storage); + _STLP_STD::swap(_M_finish, __s._M_finish); + } +#else + _STLP_STD::swap(_M_start, __s._M_start); + _M_end_of_storage.swap(__s._M_end_of_storage); + _STLP_STD::swap(_M_finish, __s._M_finish); +#endif /* _STLP_USE_SHORT_STRING_OPTIM */ + } + + void _STLP_FUNCTION_THROWS _M_throw_length_error() const; + void _STLP_FUNCTION_THROWS _M_throw_out_of_range() const; +}; + +#undef _STLP_SHORT_STRING_SZ + +#if defined (_STLP_USE_TEMPLATE_EXPORT) +_STLP_EXPORT_TEMPLATE_CLASS _String_base >; +# if defined (_STLP_HAS_WCHAR_T) +_STLP_EXPORT_TEMPLATE_CLASS _String_base >; +# endif +#endif /* _STLP_USE_TEMPLATE_EXPORT */ + +_STLP_MOVE_TO_STD_NAMESPACE + +_STLP_END_NAMESPACE + +#endif /* _STLP_STRING_BASE_H */ + +/* + * Local Variables: + * mode:C++ + * End: + */