Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

503 lines
12 KiB

  1. // memory standard header
  2. #pragma once
  3. #ifndef _MEMORY_
  4. #define _MEMORY_
  5. #include <iterator>
  6. #include <xmemory>
  7. #pragma pack(push,8)
  8. #pragma warning(push,3)
  9. _STD_BEGIN
  10. // TEMPLATE FUNCTION get_temporary_buffer
  11. template<class _Ty> inline
  12. pair<_Ty _FARQ *, _PDFT>
  13. get_temporary_buffer(_PDFT _Count)
  14. { // get raw temporary buffer of up to _Count elements
  15. _Ty _FARQ *_Pbuf;
  16. for (_Pbuf = 0; 0 < _Count; _Count /= 2)
  17. if ((_Pbuf = (_Ty _FARQ *)operator new(
  18. (_SIZT)_Count * sizeof (_Ty), nothrow)) != 0)
  19. break;
  20. return (pair<_Ty _FARQ *, _PDFT>(_Pbuf, _Count));
  21. }
  22. // TEMPLATE FUNCTION return_temporary_buffer
  23. template<class _Ty> inline
  24. void return_temporary_buffer(_Ty *_Pbuf)
  25. { // delete raw temporary buffer
  26. operator delete(_Pbuf);
  27. }
  28. // TEMPLATE FUNCTION uninitialized_copy
  29. template<class _InIt,
  30. class _FwdIt> inline
  31. _FwdIt uninitialized_copy(_InIt _First, _InIt _Last, _FwdIt _Dest)
  32. { // copy [_First, _Last) to raw _Dest
  33. return (_Uninit_copy(_First, _Last, _Dest,
  34. _Ptr_cat(_First, _Dest)));
  35. }
  36. template<class _InIt,
  37. class _FwdIt> inline
  38. _FwdIt _Uninit_copy(_InIt _First, _InIt _Last, _FwdIt _Dest,
  39. _Nonscalar_ptr_iterator_tag)
  40. { // copy [_First, _Last) to raw _Dest, arbitrary type
  41. _FwdIt _Next = _Dest;
  42. _TRY_BEGIN
  43. for (; _First != _Last; ++_Dest, ++_First)
  44. _Construct(&*_Dest, *_First);
  45. _CATCH_ALL
  46. for (; _Next != _Dest; ++_Next)
  47. _Destroy(&*_Next);
  48. _RERAISE;
  49. _CATCH_END
  50. return (_Dest);
  51. }
  52. template<class _Ty> inline
  53. _Ty *_Uninit_copy(const _Ty *_First, const _Ty *_Last, _Ty *_Dest,
  54. _Scalar_ptr_iterator_tag)
  55. { // copy [_First, _Last) to raw _Dest, scalar type
  56. size_t _Count = (size_t)(_Last - _First);
  57. return ((_Ty *)memmove(&*_Dest, &*_First,
  58. _Count * sizeof (*_First)) + _Count); // NB: non-overlapping move
  59. }
  60. // TEMPLATE FUNCTION _Uninitialized_copy WITH ALLOCATOR
  61. template<class _InIt,
  62. class _FwdIt,
  63. class _Alloc> inline
  64. _FwdIt _Uninitialized_copy(_InIt _First, _InIt _Last, _FwdIt _Dest,
  65. _Alloc& _Al)
  66. { // copy [_First, _Last) to raw _Dest, using _Al
  67. return (_Uninit_copy(_First, _Last, _Dest, _Al,
  68. _Ptr_cat(_First, _Dest)));
  69. }
  70. template<class _InIt,
  71. class _FwdIt,
  72. class _Alloc> inline
  73. _FwdIt _Uninit_copy(_InIt _First, _InIt _Last, _FwdIt _Dest,
  74. _Alloc& _Al, _Nonscalar_ptr_iterator_tag)
  75. { // copy [_First, _Last) to raw _Dest, using _Al, arbitrary type
  76. _FwdIt _Next = _Dest;
  77. _TRY_BEGIN
  78. for (; _First != _Last; ++_Dest, ++_First)
  79. _Al.construct(_Dest, *_First);
  80. _CATCH_ALL
  81. for (; _Next != _Dest; ++_Next)
  82. _Al.destroy(_Next);
  83. _RERAISE;
  84. _CATCH_END
  85. return (_Dest);
  86. }
  87. template<class _Ty> inline
  88. _Ty *_Uninit_copy(const _Ty *_First, const _Ty *_Last, _Ty *_Dest,
  89. allocator<_Ty>&, _Scalar_ptr_iterator_tag)
  90. { // copy [_First, _Last) to raw _Dest, scalar type
  91. size_t _Count = (size_t)(_Last - _First);
  92. return ((_Ty *)memmove(&*_Dest, &*_First,
  93. _Count * sizeof (*_First)) + _Count); // NB: non-overlapping move
  94. }
  95. // TEMPLATE FUNCTION uninitialized_fill
  96. template<class _FwdIt,
  97. class _Tval> inline
  98. void uninitialized_fill(_FwdIt _First, _FwdIt _Last, const _Tval& _Val)
  99. { // copy _Val throughout raw [_First, _Last)
  100. _Uninit_fill(_First, _Last, _Val, _Ptr_cat(_First, _First));
  101. }
  102. template<class _FwdIt,
  103. class _Tval> inline
  104. void _Uninit_fill(_FwdIt _First, _FwdIt _Last, const _Tval& _Val,
  105. _Nonscalar_ptr_iterator_tag)
  106. { // copy _Val throughout raw [_First, _Last), arbitrary type
  107. _FwdIt _Next = _First;
  108. _TRY_BEGIN
  109. for (; _First != _Last; ++_First)
  110. _Construct(&*_First, _Val);
  111. _CATCH_ALL
  112. for (; _Next != _First; ++_Next)
  113. _Destroy(&*_Next);
  114. _RERAISE;
  115. _CATCH_END
  116. }
  117. template<class _Ty,
  118. class _Tval> inline
  119. void _Uninit_fill(_Ty *_First, _Ty *_Last, const _Tval& _Val,
  120. _Scalar_ptr_iterator_tag)
  121. { // copy _Val throughout raw [_First, _Last), scalar type
  122. std::fill(_First, _Last, _Val);
  123. }
  124. // TEMPLATE FUNCTION uninitialized_fill_n
  125. template<class _FwdIt,
  126. class _Diff,
  127. class _Tval> inline
  128. void uninitialized_fill_n(_FwdIt _First, _Diff _Count, const _Tval& _Val)
  129. { // copy _Count *_Val to raw _First
  130. _Uninit_fill_n(_First, _Count, _Val, _Ptr_cat(_First, _First));
  131. }
  132. template<class _FwdIt,
  133. class _Diff,
  134. class _Tval> inline
  135. void _Uninit_fill_n(_FwdIt _First, _Diff _Count, const _Tval& _Val,
  136. _Nonscalar_ptr_iterator_tag)
  137. { // copy _Count *_Val to raw _First, arbitrary type
  138. _FwdIt _Next = _First;
  139. _TRY_BEGIN
  140. for (; 0 < _Count; --_Count, ++_First)
  141. _Construct(&*_First, _Val);
  142. _CATCH_ALL
  143. for (; _Next != _First; ++_Next)
  144. _Destroy(&*_Next);
  145. _RERAISE;
  146. _CATCH_END
  147. }
  148. template<class _Ty,
  149. class _Diff,
  150. class _Tval> inline
  151. void _Uninit_fill_n(_Ty *_First, _Diff _Count, const _Tval& _Val,
  152. _Scalar_ptr_iterator_tag)
  153. { // copy _Count *_Val to raw _First, scalar type
  154. std::fill_n(_First, _Count, _Val);
  155. }
  156. // TEMPLATE FUNCTION _Uninitialized_fill_n WITH ALLOCATOR
  157. template<class _FwdIt,
  158. class _Diff,
  159. class _Tval,
  160. class _Alloc> inline
  161. void _Uninitialized_fill_n(_FwdIt _First, _Diff _Count,
  162. const _Tval& _Val, _Alloc& _Al)
  163. { // copy _Count *_Val to raw _First, using _Al
  164. _Uninit_fill_n(_First, _Count, _Val, _Al,
  165. _Ptr_cat(_First, _First));
  166. }
  167. template<class _FwdIt,
  168. class _Diff,
  169. class _Tval,
  170. class _Alloc> inline
  171. void _Uninit_fill_n(_FwdIt _First, _Diff _Count,
  172. const _Tval& _Val, _Alloc& _Al, _Nonscalar_ptr_iterator_tag)
  173. { // copy _Count *_Val to raw _First, using _Al, arbitrary type
  174. _FwdIt _Next = _First;
  175. _TRY_BEGIN
  176. for (; 0 < _Count; --_Count, ++_First)
  177. _Al.construct(_First, _Val);
  178. _CATCH_ALL
  179. for (; _Next != _First; ++_Next)
  180. _Al.destroy(_Next);
  181. _RERAISE;
  182. _CATCH_END
  183. }
  184. template<class _Ty,
  185. class _Diff,
  186. class _Tval> inline
  187. void _Uninit_fill_n(_Ty *_First, _Diff _Count,
  188. const _Tval& _Val, allocator<_Ty>&, _Scalar_ptr_iterator_tag)
  189. { // copy _Count *_Val to raw _First, using _Al, scalar type
  190. fill_n(_First, _Count, _Val);
  191. }
  192. // TEMPLATE CLASS raw_storage_iterator
  193. template<class _FwdIt,
  194. class _Ty>
  195. class raw_storage_iterator
  196. : public _Outit
  197. { // wrap stores to raw buffer as output iterator
  198. public:
  199. typedef _FwdIt iterator_type; // retained
  200. typedef _FwdIt iter_type; // retained
  201. typedef _Ty element_type; // retained
  202. explicit raw_storage_iterator(_FwdIt _First)
  203. : _Next(_First)
  204. { // construct with iterator
  205. }
  206. raw_storage_iterator<_FwdIt, _Ty>& operator*()
  207. { // pretend to return designated value
  208. return (*this);
  209. }
  210. raw_storage_iterator<_FwdIt, _Ty>& operator=(const _Ty& _Val)
  211. { // construct value designated by stored iterator
  212. _Construct(&*_Next, _Val);
  213. return (*this);
  214. }
  215. raw_storage_iterator<_FwdIt, _Ty>& operator++()
  216. { // preincrement
  217. ++_Next;
  218. return (*this);
  219. }
  220. raw_storage_iterator<_FwdIt, _Ty> operator++(int)
  221. { // postincrement
  222. raw_storage_iterator<_FwdIt, _Ty> _Ans = *this;
  223. ++_Next;
  224. return (_Ans);
  225. }
  226. private:
  227. _FwdIt _Next; // the stored iterator
  228. };
  229. // TEMPLATE CLASS _Temp_iterator
  230. template<class _Ty>
  231. class _Temp_iterator
  232. : public _Outit
  233. { // wrap stores to temporary buffer as output iterator
  234. public:
  235. typedef _Ty _FARQ *_Pty;
  236. _Temp_iterator(_PDFT _Count = 0)
  237. { // construct from desired temporary buffer size
  238. pair<_Pty, _PDFT> _Pair =
  239. std::get_temporary_buffer<_Ty>(_Count);
  240. _Buf._Begin = _Pair.first;
  241. _Buf._Current = _Pair.first;
  242. _Buf._Hiwater = _Pair.first;
  243. _Buf._Size = _Pair.second;
  244. _Pbuf = &_Buf;
  245. }
  246. _Temp_iterator(const _Temp_iterator<_Ty>& _Right)
  247. { // construct from _Right (share active buffer)
  248. _Buf._Begin = 0; // clear stored buffer, to be tidy
  249. _Buf._Current = 0;
  250. _Buf._Hiwater = 0;
  251. _Buf._Size = 0;
  252. *this = _Right;
  253. }
  254. ~_Temp_iterator()
  255. { // destroy the object
  256. if (_Buf._Begin != 0)
  257. { // destroy any constructed elements in buffer
  258. for (_Pty _Next = _Buf._Begin;
  259. _Next != _Buf._Hiwater; ++_Next)
  260. _Destroy(&*_Next);
  261. std::return_temporary_buffer(_Buf._Begin);
  262. }
  263. }
  264. _Temp_iterator<_Ty>& operator=(const _Temp_iterator<_Ty>& _Right)
  265. { // assign _Right (share active buffer)
  266. _Pbuf = _Right._Pbuf;
  267. return (*this);
  268. }
  269. _Temp_iterator<_Ty>& operator=(const _Ty& _Val)
  270. { // assign or construct value into active buffer, and increment
  271. if (_Pbuf->_Current < _Pbuf->_Hiwater)
  272. *_Pbuf->_Current++ = _Val; // below high water mark, assign
  273. else
  274. { // above high water mark, construct
  275. _Construct(&*_Pbuf->_Current, _Val);
  276. _Pbuf->_Hiwater = ++_Pbuf->_Current;
  277. }
  278. return (*this);
  279. }
  280. _Temp_iterator<_Ty>& operator*()
  281. { // pretend to return designated value
  282. return (*this);
  283. }
  284. _Temp_iterator<_Ty>& operator++()
  285. { // pretend to preincrement
  286. return (*this);
  287. }
  288. _Temp_iterator<_Ty>& operator++(int)
  289. { // pretend to postincrement
  290. return (*this);
  291. }
  292. _Temp_iterator<_Ty>& _Init()
  293. { // set pointer at beginning of buffer
  294. _Pbuf->_Current = _Pbuf->_Begin;
  295. return (*this);
  296. }
  297. _Pty _First() const
  298. { // return pointer to beginning of buffer
  299. return (_Pbuf->_Begin);
  300. }
  301. _Pty _Last() const
  302. { // return pointer past end of buffer contents
  303. return (_Pbuf->_Current);
  304. }
  305. _PDFT _Maxlen() const
  306. { // return size of buffer
  307. return (_Pbuf->_Size);
  308. }
  309. private:
  310. struct _Bufpar
  311. { // control information for a temporary buffer
  312. _Pty _Begin; // pointer to beginning of buffer
  313. _Pty _Current; // pointer to next available element
  314. _Pty _Hiwater; // pointer to first unconstructed element
  315. _PDFT _Size; // length of buffer
  316. };
  317. _Bufpar _Buf; // buffer control stored in iterator
  318. _Bufpar *_Pbuf; // pointer to active buffer control
  319. };
  320. // TEMPLATE CLASS auto_ptr
  321. template<class _Ty>
  322. class auto_ptr;
  323. template<class _Ty>
  324. struct auto_ptr_ref
  325. { // proxy reference for auto_ptr copying
  326. auto_ptr_ref(auto_ptr<_Ty>& _Right)
  327. : _Ref(_Right)
  328. { // construct from compatible auto_ptr
  329. }
  330. auto_ptr<_Ty>& _Ref; // reference to constructor argument
  331. };
  332. template<class _Ty>
  333. class auto_ptr
  334. { // wrap an object pointer to ensure destruction
  335. public:
  336. typedef _Ty element_type;
  337. explicit auto_ptr(_Ty *_Ptr = 0) _THROW0()
  338. : _Myptr(_Ptr)
  339. { // construct from object pointer
  340. }
  341. auto_ptr(auto_ptr<_Ty>& _Right) _THROW0()
  342. : _Myptr(_Right.release())
  343. { // construct by assuming pointer from _Right auto_ptr
  344. }
  345. auto_ptr(auto_ptr_ref<_Ty> _Right) _THROW0()
  346. : _Myptr(_Right._Ref.release())
  347. { // construct by assuming pointer from _Right auto_ptr_ref
  348. }
  349. template<class _Other>
  350. operator auto_ptr<_Other>() _THROW0()
  351. { // convert to compatible auto_ptr
  352. return (auto_ptr<_Other>(*this));
  353. }
  354. template<class _Other>
  355. operator auto_ptr_ref<_Other>() _THROW0()
  356. { // convert to compatible auto_ptr_ref
  357. return (auto_ptr_ref<_Other>(*this));
  358. }
  359. template<class _Other>
  360. auto_ptr<_Ty>& operator=(auto_ptr<_Other>& _Right) _THROW0()
  361. { // assign compatible _Right (assume pointer)
  362. reset(_Right.release());
  363. return (*this);
  364. }
  365. template<class _Other>
  366. auto_ptr(auto_ptr<_Other>& _Right) _THROW0()
  367. : _Myptr(_Right.release())
  368. { // construct by assuming pointer from _Right
  369. }
  370. auto_ptr<_Ty>& operator=(auto_ptr<_Ty>& _Right) _THROW0()
  371. { // assign compatible _Right (assume pointer)
  372. reset(_Right.release());
  373. return (*this);
  374. }
  375. auto_ptr<_Ty>& operator=(auto_ptr_ref<_Ty>& _Right) throw ()
  376. { // assign compatible _Right._Ref (assume pointer)
  377. reset(_Right._Ref.release());
  378. return (*this);
  379. }
  380. ~auto_ptr()
  381. { // destroy the object
  382. delete _Myptr;
  383. }
  384. _Ty& operator*() const _THROW0()
  385. { // return designated value
  386. return (*get());
  387. }
  388. _Ty *operator->() const _THROW0()
  389. { // return pointer to class object
  390. return (get());
  391. }
  392. _Ty *get() const _THROW0()
  393. { // return wrapped pointer
  394. return (_Myptr);
  395. }
  396. _Ty *release() _THROW0()
  397. { // return wrapped pointer and give up ownership
  398. _Ty *_Tmp = _Myptr;
  399. _Myptr = 0;
  400. return (_Tmp);
  401. }
  402. void reset(_Ty* _Ptr = 0)
  403. { // destroy designated object and store new pointer
  404. if (_Ptr != _Myptr)
  405. delete _Myptr;
  406. _Myptr = _Ptr;
  407. }
  408. private:
  409. _Ty *_Myptr; // the wrapped object pointer
  410. };
  411. _STD_END
  412. #pragma warning(pop)
  413. #pragma pack(pop)
  414. #endif /* _MEMORY_ */
  415. /*
  416. * Copyright (c) 1992-2001 by P.J. Plauger. ALL RIGHTS RESERVED.
  417. * Consult your license regarding permissions and restrictions.
  418. */
  419. /*
  420. * This file is derived from software bearing the following
  421. * restrictions:
  422. *
  423. * Copyright (c) 1994
  424. * Hewlett-Packard Company
  425. *
  426. * Permission to use, copy, modify, distribute and sell this
  427. * software and its documentation for any purpose is hereby
  428. * granted without fee, provided that the above copyright notice
  429. * appear in all copies and that both that copyright notice and
  430. * this permission notice appear in supporting documentation.
  431. * Hewlett-Packard Company makes no representations about the
  432. * suitability of this software for any purpose. It is provided
  433. * "as is" without express or implied warranty.
  434. V3.10:0009 */