1 #ifndef BOOST_RANGE_ATL_HPP 2 #define BOOST_RANGE_ATL_HPP 3 4 5 6 7 // Boost.Range ATL Extension 8 // 9 // Copyright Shunsuke Sogame 2005-2006. 10 // Distributed under the Boost Software License, Version 1.0. 11 // (See accompanying file LICENSE_1_0.txt or copy at 12 // http://www.boost.org/LICENSE_1_0.txt) 13 14 15 16 17 // config 18 // 19 20 21 #include <atldef.h> // _ATL_VER 22 23 24 #if !defined(BOOST_RANGE_ATL_NO_COLLECTIONS) 25 #if (_ATL_VER < 0x0700) 26 #define BOOST_RANGE_ATL_NO_COLLECTIONS 27 #endif 28 #endif 29 30 31 #if !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 32 #if (_ATL_VER < 0x0700) // dubious 33 #define BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX 34 #endif 35 #endif 36 37 38 // forward declarations 39 // 40 41 42 #include <basetyps.h> // IID 43 44 45 namespace ATL { 46 47 48 #if !defined(BOOST_RANGE_ATL_NO_COLLECTIONS) 49 50 51 // arrays 52 // 53 template< class E, class ETraits > 54 class CAtlArray; 55 56 template< class E > 57 class CAutoPtrArray; 58 59 template< class I, const IID *piid > 60 class CInterfaceArray; 61 62 63 // lists 64 // 65 template< class E, class ETraits > 66 class CAtlList; 67 68 template< class E > 69 class CAutoPtrList; 70 71 template< class E, class Allocator > 72 class CHeapPtrList; 73 74 template< class I, const IID *piid > 75 class CInterfaceList; 76 77 78 // maps 79 // 80 template< class K, class V, class KTraits, class VTraits > 81 class CAtlMap; 82 83 template< class K, class V, class KTraits, class VTraits > 84 class CRBTree; 85 86 template< class K, class V, class KTraits, class VTraits > 87 class CRBMap; 88 89 template< class K, class V, class KTraits, class VTraits > 90 class CRBMultiMap; 91 92 93 // strings 94 // 95 #if !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLESTRING) 96 template< class BaseType, bool t_bMFCDLL > 97 class CSimpleStringT; 98 #else 99 template< class BaseType > 100 class CSimpleStringT; 101 #endif 102 103 template< class BaseType, class StringTraits > 104 class CStringT; 105 106 template< class StringType, int t_nChars > 107 class CFixedStringT; 108 109 template< class BaseType, const int t_nSize > 110 class CStaticString; 111 112 113 #endif // !defined(BOOST_RANGE_ATL_NO_COLLECTIONS) 114 115 116 // simples 117 // 118 #if !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 119 120 template< class T, class TEqual > 121 class CSimpleArray; 122 123 template< class TKey, class TVal, class TEqual > 124 class CSimpleMap; 125 126 #else 127 128 template< class T > 129 class CSimpleArray; 130 131 template< class T > 132 class CSimpleValArray; 133 134 template< class TKey, class TVal > 135 class CSimpleMap; 136 137 #endif // !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 138 139 140 // pointers 141 // 142 template< class E > 143 class CAutoPtr; 144 145 template< class T > 146 class CComPtr; 147 148 template< class T, const IID *piid > 149 class CComQIPtr; 150 151 template< class E, class Allocator > 152 class CHeapPtr; 153 154 template< class T > 155 class CAdapt; 156 157 158 } // namespace ATL 159 160 161 162 163 // indirect_iterator customizations 164 // 165 166 167 #include <boost/mpl/identity.hpp> 168 #include <boost/pointee.hpp> 169 170 171 namespace boost { 172 173 174 template< class E > 175 struct pointee< ATL::CAutoPtr<E> > : 176 mpl::identity<E> 177 { }; 178 179 template< class T > 180 struct pointee< ATL::CComPtr<T> > : 181 mpl::identity<T> 182 { }; 183 184 template< class T, const IID *piid > 185 struct pointee< ATL::CComQIPtr<T, piid> > : 186 mpl::identity<T> 187 { }; 188 189 template< class E, class Allocator > 190 struct pointee< ATL::CHeapPtr<E, Allocator> > : 191 mpl::identity<E> 192 { }; 193 194 template< class T > 195 struct pointee< ATL::CAdapt<T> > : 196 pointee<T> 197 { }; 198 199 200 } // namespace boost 201 202 203 204 205 // extended customizations 206 // 207 208 209 #include <boost/iterator/indirect_iterator.hpp> 210 #include <boost/iterator/zip_iterator.hpp> 211 #include <boost/range/detail/microsoft.hpp> 212 #include <boost/tuple/tuple.hpp> 213 #include <atlbase.h> // CComBSTR 214 215 216 namespace boost { namespace range_detail_microsoft { 217 218 219 #if !defined(BOOST_RANGE_ATL_NO_COLLECTIONS) 220 221 222 // arrays 223 // 224 225 struct atl_array_functions : 226 array_functions 227 { 228 template< class Iterator, class X > 229 Iterator end(X& x) // redefine 230 { 231 return x.GetData() + x.GetCount(); // no 'GetSize()' 232 } 233 }; 234 235 236 template< class E, class ETraits > 237 struct customization< ATL::CAtlArray<E, ETraits> > : 238 atl_array_functions 239 { 240 template< class X > 241 struct meta 242 { 243 typedef E val_t; 244 245 typedef val_t *mutable_iterator; 246 typedef val_t const *const_iterator; 247 }; 248 }; 249 250 251 template< class E > 252 struct customization< ATL::CAutoPtrArray<E> > : 253 atl_array_functions 254 { 255 template< class X > 256 struct meta 257 { 258 // ATL::CAutoPtr/CHeapPtr is no assignable. 259 typedef ATL::CAutoPtr<E> val_t; 260 typedef val_t *miter_t; 261 typedef val_t const *citer_t; 262 263 typedef indirect_iterator<miter_t> mutable_iterator; 264 typedef indirect_iterator<citer_t> const_iterator; 265 }; 266 }; 267 268 269 template< class I, const IID *piid > 270 struct customization< ATL::CInterfaceArray<I, piid> > : 271 atl_array_functions 272 { 273 template< class X > 274 struct meta 275 { 276 typedef ATL::CComQIPtr<I, piid> val_t; 277 278 typedef val_t *mutable_iterator; 279 typedef val_t const *const_iterator; 280 }; 281 }; 282 283 284 template< class E, class ETraits > 285 struct customization< ATL::CAtlList<E, ETraits> > : 286 list_functions 287 { 288 template< class X > 289 struct meta 290 { 291 typedef E val_t; 292 293 typedef list_iterator<X, val_t> mutable_iterator; 294 typedef list_iterator<X const, val_t const> const_iterator; 295 }; 296 }; 297 298 299 struct indirected_list_functions 300 { 301 template< class Iterator, class X > 302 Iterator begin(X& x) 303 { 304 typedef typename Iterator::base_type base_t; // == list_iterator 305 return Iterator(base_t(x, x.GetHeadPosition())); 306 } 307 308 template< class Iterator, class X > 309 Iterator end(X& x) 310 { 311 typedef typename Iterator::base_type base_t; 312 return Iterator(base_t(x, POSITION(0))); 313 } 314 }; 315 316 317 template< class E > 318 struct customization< ATL::CAutoPtrList<E> > : 319 indirected_list_functions 320 { 321 template< class X > 322 struct meta 323 { 324 typedef ATL::CAutoPtr<E> val_t; 325 typedef list_iterator<X, val_t> miter_t; 326 typedef list_iterator<X const, val_t const> citer_t; 327 328 typedef indirect_iterator<miter_t> mutable_iterator; 329 typedef indirect_iterator<citer_t> const_iterator; 330 }; 331 }; 332 333 334 template< class E, class Allocator > 335 struct customization< ATL::CHeapPtrList<E, Allocator> > : 336 indirected_list_functions 337 { 338 template< class X > 339 struct meta 340 { 341 typedef ATL::CHeapPtr<E, Allocator> val_t; 342 typedef list_iterator<X, val_t> miter_t; 343 typedef list_iterator<X const, val_t const> citer_t; 344 345 typedef indirect_iterator<miter_t> mutable_iterator; 346 typedef indirect_iterator<citer_t> const_iterator; 347 }; 348 }; 349 350 351 template< class I, const IID *piid > 352 struct customization< ATL::CInterfaceList<I, piid> > : 353 list_functions 354 { 355 template< class X > 356 struct meta 357 { 358 typedef ATL::CComQIPtr<I, piid> val_t; 359 360 typedef list_iterator<X, val_t> mutable_iterator; 361 typedef list_iterator<X const, val_t const> const_iterator; 362 }; 363 }; 364 365 366 // maps 367 // 368 369 struct atl_rb_tree_tag 370 { }; 371 372 template< > 373 struct customization< atl_rb_tree_tag > : 374 indirected_list_functions 375 { 376 template< class X > 377 struct meta 378 { 379 typedef typename X::CPair val_t; 380 381 typedef list_iterator<X, val_t *, val_t *> miter_t; 382 typedef list_iterator<X const, val_t const *, val_t const *> citer_t; 383 384 typedef indirect_iterator<miter_t> mutable_iterator; 385 typedef indirect_iterator<citer_t> const_iterator; 386 }; 387 }; 388 389 390 template< class K, class V, class KTraits, class VTraits > 391 struct customization< ATL::CAtlMap<K, V, KTraits, VTraits> > : 392 customization< atl_rb_tree_tag > 393 { 394 template< class Iterator, class X > 395 Iterator begin(X& x) // redefine 396 { 397 typedef typename Iterator::base_type base_t; // == list_iterator 398 return Iterator(base_t(x, x.GetStartPosition())); // no 'GetHeadPosition' 399 } 400 }; 401 402 403 // strings 404 // 405 406 struct atl_string_tag 407 { }; 408 409 template< > 410 struct customization< atl_string_tag > 411 { 412 template< class X > 413 struct meta 414 { 415 typedef typename X::PXSTR mutable_iterator; 416 typedef typename X::PCXSTR const_iterator; 417 }; 418 419 template< class Iterator, class X > beginboost::range_detail_microsoft::customization420 typename mutable_<Iterator, X>::type begin(X& x) 421 { 422 return x.GetBuffer(0); 423 } 424 425 template< class Iterator, class X > 426 Iterator begin(X const& x) 427 { 428 return x.GetString(); 429 } 430 431 template< class Iterator, class X > 432 Iterator end(X& x) 433 { 434 return begin<Iterator>(x) + x.GetLength(); 435 } 436 }; 437 438 439 template< class BaseType, const int t_nSize > 440 struct customization< ATL::CStaticString<BaseType, t_nSize> > 441 { 442 template< class X > 443 struct meta 444 { 445 typedef BaseType const *mutable_iterator; 446 typedef mutable_iterator const_iterator; 447 }; 448 449 template< class Iterator, class X > 450 Iterator begin(X const& x) 451 { 452 return x; 453 } 454 455 template< class Iterator, class X > 456 Iterator end(X const& x) 457 { 458 return begin<Iterator>(x) + X::GetLength(); 459 } 460 }; 461 462 463 #endif // !defined(BOOST_RANGE_ATL_NO_COLLECTIONS) 464 465 466 template< > 467 struct customization< ATL::CComBSTR > 468 { 469 template< class X > 470 struct meta 471 { 472 typedef OLECHAR *mutable_iterator; 473 typedef OLECHAR const *const_iterator; 474 }; 475 476 template< class Iterator, class X > 477 Iterator begin(X& x) 478 { 479 return x.operator BSTR(); 480 } 481 482 template< class Iterator, class X > 483 Iterator end(X& x) 484 { 485 return begin<Iterator>(x) + x.Length(); 486 } 487 }; 488 489 490 // simples 491 // 492 493 #if !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 494 template< class T, class TEqual > 495 struct customization< ATL::CSimpleArray<T, TEqual> > : 496 #else 497 template< class T > 498 struct customization< ATL::CSimpleArray<T> > : 499 #endif 500 array_functions 501 { 502 template< class X > 503 struct meta 504 { 505 typedef T val_t; 506 507 typedef val_t *mutable_iterator; 508 typedef val_t const *const_iterator; 509 }; 510 }; 511 512 513 #if defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 514 515 template< class T > 516 struct customization< ATL::CSimpleValArray<T> > : 517 array_functions 518 { 519 template< class X > 520 struct meta 521 { 522 typedef T val_t; 523 524 typedef val_t *mutable_iterator; 525 typedef val_t const *const_iterator; 526 }; 527 }; 528 529 #endif // defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 530 531 532 #if !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 533 template< class TKey, class TVal, class TEqual > 534 struct customization< ATL::CSimpleMap<TKey, TVal, TEqual> > 535 #else 536 template< class TKey, class TVal > 537 struct customization< ATL::CSimpleMap<TKey, TVal> > 538 #endif 539 { 540 template< class X > 541 struct meta 542 { 543 typedef TKey k_val_t; 544 typedef k_val_t *k_miter_t; 545 typedef k_val_t const *k_citer_t; 546 547 typedef TVal v_val_t; 548 typedef v_val_t *v_miter_t; 549 typedef v_val_t const *v_citer_t; 550 551 // Topic: 552 // 'std::pair' can't contain references 553 // because of reference to reference problem. 554 555 typedef zip_iterator< tuple<k_miter_t, v_miter_t> > mutable_iterator; 556 typedef zip_iterator< tuple<k_citer_t, v_citer_t> > const_iterator; 557 }; 558 559 template< class Iterator, class X > 560 Iterator begin(X& x) 561 { 562 return Iterator(boost::make_tuple(x.m_aKey, x.m_aVal)); 563 } 564 565 template< class Iterator, class X > 566 Iterator end(X& x) 567 { 568 return Iterator(boost::make_tuple(x.m_aKey + x.GetSize(), x.m_aVal + x.GetSize())); 569 } 570 }; 571 572 573 } } // namespace boost::range_detail_microsoft 574 575 576 577 578 // range customizations 579 // 580 581 582 #if !defined(BOOST_RANGE_ATL_NO_COLLECTIONS) 583 584 585 // arrays 586 // 587 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 588 boost::range_detail_microsoft::using_type_as_tag, 589 (ATL, BOOST_PP_NIL), CAtlArray, 2 590 ) 591 592 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 593 boost::range_detail_microsoft::using_type_as_tag, 594 (ATL, BOOST_PP_NIL), CAutoPtrArray, 1 595 ) 596 597 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 598 boost::range_detail_microsoft::using_type_as_tag, 599 (ATL, BOOST_PP_NIL), CInterfaceArray, (class)(const IID *) 600 ) 601 602 603 // lists 604 // 605 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 606 boost::range_detail_microsoft::using_type_as_tag, 607 (ATL, BOOST_PP_NIL), CAtlList, 2 608 ) 609 610 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 611 boost::range_detail_microsoft::using_type_as_tag, 612 (ATL, BOOST_PP_NIL), CAutoPtrList, 1 613 ) 614 615 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 616 boost::range_detail_microsoft::using_type_as_tag, 617 (ATL, BOOST_PP_NIL), CHeapPtrList, 2 618 ) 619 620 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 621 boost::range_detail_microsoft::using_type_as_tag, 622 (ATL, BOOST_PP_NIL), CInterfaceList, (class)(const IID *) 623 ) 624 625 626 //maps 627 // 628 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 629 boost::range_detail_microsoft::using_type_as_tag, 630 (ATL, BOOST_PP_NIL), CAtlMap, 4 631 ) 632 633 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 634 boost::range_detail_microsoft::atl_rb_tree_tag, 635 (ATL, BOOST_PP_NIL), CRBTree, 4 636 ) 637 638 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 639 boost::range_detail_microsoft::atl_rb_tree_tag, 640 (ATL, BOOST_PP_NIL), CRBMap, 4 641 ) 642 643 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 644 boost::range_detail_microsoft::atl_rb_tree_tag, 645 (ATL, BOOST_PP_NIL), CRBMultiMap, 4 646 ) 647 648 649 // strings 650 // 651 #if !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLESTRING) 652 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 653 boost::range_detail_microsoft::atl_string_tag, 654 (ATL, BOOST_PP_NIL), CSimpleStringT, (class)(bool) 655 ) 656 #else 657 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 658 boost::range_detail_microsoft::atl_string_tag, 659 (ATL, BOOST_PP_NIL), CSimpleStringT, 1 660 ) 661 #endif 662 663 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 664 boost::range_detail_microsoft::atl_string_tag, 665 (ATL, BOOST_PP_NIL), CStringT, 2 666 ) 667 668 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 669 boost::range_detail_microsoft::atl_string_tag, 670 (ATL, BOOST_PP_NIL), CFixedStringT, (class)(int) 671 ) 672 673 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 674 boost::range_detail_microsoft::using_type_as_tag, 675 (ATL, BOOST_PP_NIL), CStaticString, (class)(const int) 676 ) 677 678 679 #endif // !defined(BOOST_RANGE_ATL_NO_COLLECTIONS) 680 681 682 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TYPE( 683 boost::range_detail_microsoft::using_type_as_tag, 684 (ATL, BOOST_PP_NIL), CComBSTR 685 ) 686 687 688 // simples 689 // 690 #if !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 691 692 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 693 boost::range_detail_microsoft::using_type_as_tag, 694 (ATL, BOOST_PP_NIL), CSimpleArray, 2 695 ) 696 697 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 698 boost::range_detail_microsoft::using_type_as_tag, 699 (ATL, BOOST_PP_NIL), CSimpleMap, 3 700 ) 701 702 #else 703 704 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 705 boost::range_detail_microsoft::using_type_as_tag, 706 (ATL, BOOST_PP_NIL), CSimpleArray, 1 707 ) 708 709 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 710 boost::range_detail_microsoft::using_type_as_tag, 711 (ATL, BOOST_PP_NIL), CSimpleMap, 2 712 ) 713 714 BOOST_RANGE_DETAIL_MICROSOFT_CUSTOMIZATION_TEMPLATE( 715 boost::range_detail_microsoft::using_type_as_tag, 716 (ATL, BOOST_PP_NIL), CSimpleValArray, 1 717 ) 718 719 #endif // !defined(BOOST_RANGE_ATL_HAS_OLD_CSIMPLE_XXX) 720 721 722 723 724 #endif 725