1132720Skan// Debugging bitset implementation -*- C++ -*- 2132720Skan 3169691Skan// Copyright (C) 2003, 2004, 2005 4132720Skan// Free Software Foundation, Inc. 5132720Skan// 6132720Skan// This file is part of the GNU ISO C++ Library. This library is free 7132720Skan// software; you can redistribute it and/or modify it under the 8132720Skan// terms of the GNU General Public License as published by the 9132720Skan// Free Software Foundation; either version 2, or (at your option) 10132720Skan// any later version. 11132720Skan 12132720Skan// This library is distributed in the hope that it will be useful, 13132720Skan// but WITHOUT ANY WARRANTY; without even the implied warranty of 14132720Skan// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15132720Skan// GNU General Public License for more details. 16132720Skan 17132720Skan// You should have received a copy of the GNU General Public License along 18132720Skan// with this library; see the file COPYING. If not, write to the Free 19169691Skan// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, 20132720Skan// USA. 21132720Skan 22132720Skan// As a special exception, you may use this file as part of a free software 23132720Skan// library without restriction. Specifically, if other files instantiate 24132720Skan// templates or use macros or inline functions from this file, or you compile 25132720Skan// this file and link it with other files to produce an executable, this 26132720Skan// file does not by itself cause the resulting executable to be covered by 27132720Skan// the GNU General Public License. This exception does not however 28132720Skan// invalidate any other reasons why the executable file might be covered by 29132720Skan// the GNU General Public License. 30132720Skan 31169691Skan/** @file debug/bitset 32169691Skan * This file is a GNU debug extension to the Standard C++ Library. 33169691Skan */ 34169691Skan 35132720Skan#ifndef _GLIBCXX_DEBUG_BITSET 36132720Skan#define _GLIBCXX_DEBUG_BITSET 37132720Skan 38132720Skan#include <bitset> 39132720Skan#include <debug/safe_sequence.h> 40132720Skan#include <debug/safe_iterator.h> 41132720Skan 42169691Skannamespace std 43132720Skan{ 44169691Skannamespace __debug 45169691Skan{ 46132720Skan template<size_t _Nb> 47132720Skan class bitset 48132720Skan : public _GLIBCXX_STD::bitset<_Nb>, 49132720Skan public __gnu_debug::_Safe_sequence_base 50132720Skan { 51132720Skan typedef _GLIBCXX_STD::bitset<_Nb> _Base; 52132720Skan typedef __gnu_debug::_Safe_sequence_base _Safe_base; 53132720Skan 54132720Skan public: 55132720Skan // bit reference: 56132720Skan class reference 57132720Skan : private _Base::reference, public __gnu_debug::_Safe_iterator_base 58132720Skan { 59132720Skan typedef typename _Base::reference _Base_ref; 60132720Skan 61132720Skan friend class bitset; 62132720Skan reference(); 63132720Skan 64132720Skan reference(const _Base_ref& __base, bitset* __seq) 65132720Skan : _Base_ref(__base), _Safe_iterator_base(__seq, false) 66132720Skan { } 67132720Skan 68132720Skan public: 69132720Skan reference(const reference& __x) 70132720Skan : _Base_ref(__x), _Safe_iterator_base(__x, false) 71132720Skan { } 72132720Skan 73132720Skan reference& 74132720Skan operator=(bool __x) 75132720Skan { 76132720Skan _GLIBCXX_DEBUG_VERIFY(! this->_M_singular(), 77169691Skan _M_message(__gnu_debug::__msg_bad_bitset_write) 78132720Skan ._M_iterator(*this)); 79132720Skan *static_cast<_Base_ref*>(this) = __x; 80132720Skan return *this; 81132720Skan } 82132720Skan 83132720Skan reference& 84132720Skan operator=(const reference& __x) 85132720Skan { 86132720Skan _GLIBCXX_DEBUG_VERIFY(! __x._M_singular(), 87169691Skan _M_message(__gnu_debug::__msg_bad_bitset_read) 88132720Skan ._M_iterator(__x)); 89132720Skan _GLIBCXX_DEBUG_VERIFY(! this->_M_singular(), 90169691Skan _M_message(__gnu_debug::__msg_bad_bitset_write) 91132720Skan ._M_iterator(*this)); 92132720Skan *static_cast<_Base_ref*>(this) = __x; 93132720Skan return *this; 94132720Skan } 95132720Skan 96132720Skan bool 97132720Skan operator~() const 98132720Skan { 99132720Skan _GLIBCXX_DEBUG_VERIFY(! this->_M_singular(), 100169691Skan _M_message(__gnu_debug::__msg_bad_bitset_read) 101132720Skan ._M_iterator(*this)); 102132720Skan return ~(*static_cast<const _Base_ref*>(this)); 103132720Skan } 104132720Skan 105132720Skan operator bool() const 106132720Skan { 107132720Skan _GLIBCXX_DEBUG_VERIFY(! this->_M_singular(), 108169691Skan _M_message(__gnu_debug::__msg_bad_bitset_read) 109132720Skan ._M_iterator(*this)); 110132720Skan return *static_cast<const _Base_ref*>(this); 111132720Skan } 112132720Skan 113132720Skan reference& 114132720Skan flip() 115132720Skan { 116132720Skan _GLIBCXX_DEBUG_VERIFY(! this->_M_singular(), 117169691Skan _M_message(__gnu_debug::__msg_bad_bitset_flip) 118132720Skan ._M_iterator(*this)); 119132720Skan _Base_ref::flip(); 120132720Skan return *this; 121132720Skan } 122132720Skan }; 123132720Skan 124132720Skan // 23.3.5.1 constructors: 125132720Skan bitset() : _Base() { } 126132720Skan 127132720Skan bitset(unsigned long __val) : _Base(__val) { } 128132720Skan 129132720Skan template<typename _CharT, typename _Traits, typename _Allocator> 130132720Skan explicit 131132720Skan bitset(const std::basic_string<_CharT,_Traits,_Allocator>& __str, 132132720Skan typename std::basic_string<_CharT,_Traits,_Allocator>::size_type 133132720Skan __pos = 0, 134132720Skan typename std::basic_string<_CharT,_Traits,_Allocator>::size_type 135132720Skan __n = (std::basic_string<_CharT,_Traits,_Allocator>::npos)) 136132720Skan : _Base(__str, __pos, __n) { } 137132720Skan 138132720Skan bitset(const _Base& __x) : _Base(__x), _Safe_base() { } 139132720Skan 140132720Skan // 23.3.5.2 bitset operations: 141132720Skan bitset<_Nb>& 142132720Skan operator&=(const bitset<_Nb>& __rhs) 143132720Skan { 144132720Skan _M_base() &= __rhs; 145132720Skan return *this; 146132720Skan } 147132720Skan 148132720Skan bitset<_Nb>& 149132720Skan operator|=(const bitset<_Nb>& __rhs) 150132720Skan { 151132720Skan _M_base() |= __rhs; 152132720Skan return *this; 153132720Skan } 154132720Skan 155132720Skan bitset<_Nb>& 156132720Skan operator^=(const bitset<_Nb>& __rhs) 157132720Skan { 158132720Skan _M_base() ^= __rhs; 159132720Skan return *this; 160132720Skan } 161132720Skan 162132720Skan bitset<_Nb>& 163132720Skan operator<<=(size_t __pos) 164132720Skan { 165132720Skan _M_base() <<= __pos; 166132720Skan return *this; 167132720Skan } 168132720Skan 169132720Skan bitset<_Nb>& 170132720Skan operator>>=(size_t __pos) 171132720Skan { 172132720Skan _M_base() >>= __pos; 173132720Skan return *this; 174132720Skan } 175132720Skan 176132720Skan bitset<_Nb>& 177132720Skan set() 178132720Skan { 179132720Skan _Base::set(); 180132720Skan return *this; 181132720Skan } 182132720Skan 183132720Skan // _GLIBCXX_RESOLVE_LIB_DEFECTS 184132720Skan // 186. bitset::set() second parameter should be bool 185132720Skan bitset<_Nb>& 186132720Skan set(size_t __pos, bool __val = true) 187132720Skan { 188132720Skan _Base::set(__pos, __val); 189132720Skan return *this; 190132720Skan } 191132720Skan 192132720Skan bitset<_Nb>& 193132720Skan reset() 194132720Skan { 195132720Skan _Base::reset(); 196132720Skan return *this; 197132720Skan } 198132720Skan 199132720Skan bitset<_Nb>& 200132720Skan reset(size_t __pos) 201132720Skan { 202132720Skan _Base::reset(__pos); 203132720Skan return *this; 204132720Skan } 205132720Skan 206132720Skan bitset<_Nb> operator~() const { return bitset(~_M_base()); } 207132720Skan 208132720Skan bitset<_Nb>& 209132720Skan flip() 210132720Skan { 211132720Skan _Base::flip(); 212132720Skan return *this; 213132720Skan } 214132720Skan 215132720Skan bitset<_Nb>& 216132720Skan flip(size_t __pos) 217132720Skan { 218132720Skan _Base::flip(__pos); 219132720Skan return *this; 220132720Skan } 221132720Skan 222132720Skan // element access: 223132720Skan // _GLIBCXX_RESOLVE_LIB_DEFECTS 224132720Skan // 11. Bitset minor problems 225132720Skan reference 226132720Skan operator[](size_t __pos) 227132720Skan { 228132720Skan __glibcxx_check_subscript(__pos); 229132720Skan return reference(_M_base()[__pos], this); 230132720Skan } 231132720Skan 232132720Skan // _GLIBCXX_RESOLVE_LIB_DEFECTS 233132720Skan // 11. Bitset minor problems 234132720Skan bool 235132720Skan operator[](size_t __pos) const 236132720Skan { 237132720Skan __glibcxx_check_subscript(__pos); 238132720Skan return _M_base()[__pos]; 239132720Skan } 240132720Skan 241132720Skan using _Base::to_ulong; 242132720Skan 243132720Skan template <typename _CharT, typename _Traits, typename _Allocator> 244132720Skan std::basic_string<_CharT, _Traits, _Allocator> 245132720Skan to_string() const 246132720Skan { return _M_base().template to_string<_CharT, _Traits, _Allocator>(); } 247132720Skan 248169691Skan // _GLIBCXX_RESOLVE_LIB_DEFECTS 249169691Skan // 434. bitset::to_string() hard to use. 250169691Skan template<typename _CharT, typename _Traits> 251169691Skan std::basic_string<_CharT, _Traits, std::allocator<_CharT> > 252169691Skan to_string() const 253169691Skan { return to_string<_CharT, _Traits, std::allocator<_CharT> >(); } 254169691Skan 255169691Skan template<typename _CharT> 256169691Skan std::basic_string<_CharT, std::char_traits<_CharT>, 257169691Skan std::allocator<_CharT> > 258169691Skan to_string() const 259169691Skan { 260169691Skan return to_string<_CharT, std::char_traits<_CharT>, 261169691Skan std::allocator<_CharT> >(); 262169691Skan } 263169691Skan 264169691Skan std::basic_string<char, std::char_traits<char>, std::allocator<char> > 265169691Skan to_string() const 266169691Skan { 267169691Skan return to_string<char,std::char_traits<char>,std::allocator<char> >(); 268169691Skan } 269169691Skan 270132720Skan using _Base::count; 271132720Skan using _Base::size; 272132720Skan 273132720Skan bool 274132720Skan operator==(const bitset<_Nb>& __rhs) const 275132720Skan { return _M_base() == __rhs; } 276132720Skan 277132720Skan bool 278132720Skan operator!=(const bitset<_Nb>& __rhs) const 279132720Skan { return _M_base() != __rhs; } 280132720Skan 281132720Skan using _Base::test; 282132720Skan using _Base::any; 283132720Skan using _Base::none; 284132720Skan 285132720Skan bitset<_Nb> 286132720Skan operator<<(size_t __pos) const 287132720Skan { return bitset<_Nb>(_M_base() << __pos); } 288132720Skan 289132720Skan bitset<_Nb> 290132720Skan operator>>(size_t __pos) const 291132720Skan { return bitset<_Nb>(_M_base() >> __pos); } 292132720Skan 293132720Skan _Base& 294132720Skan _M_base() { return *this; } 295132720Skan 296132720Skan const _Base& 297132720Skan _M_base() const { return *this; } 298132720Skan }; 299132720Skan 300132720Skan template<size_t _Nb> 301132720Skan bitset<_Nb> 302132720Skan operator&(const bitset<_Nb>& __x, const bitset<_Nb>& __y) 303132720Skan { return bitset<_Nb>(__x) &= __y; } 304132720Skan 305132720Skan template<size_t _Nb> 306132720Skan bitset<_Nb> 307132720Skan operator|(const bitset<_Nb>& __x, const bitset<_Nb>& __y) 308132720Skan { return bitset<_Nb>(__x) |= __y; } 309132720Skan 310132720Skan template<size_t _Nb> 311132720Skan bitset<_Nb> 312132720Skan operator^(const bitset<_Nb>& __x, const bitset<_Nb>& __y) 313132720Skan { return bitset<_Nb>(__x) ^= __y; } 314132720Skan 315132720Skan template<typename _CharT, typename _Traits, size_t _Nb> 316132720Skan std::basic_istream<_CharT, _Traits>& 317132720Skan operator>>(std::basic_istream<_CharT, _Traits>& __is, bitset<_Nb>& __x) 318132720Skan { return __is >> __x._M_base(); } 319132720Skan 320132720Skan template<typename _CharT, typename _Traits, size_t _Nb> 321132720Skan std::basic_ostream<_CharT, _Traits>& 322132720Skan operator<<(std::basic_ostream<_CharT, _Traits>& __os, 323132720Skan const bitset<_Nb>& __x) 324132720Skan { return __os << __x._M_base(); } 325169691Skan} // namespace __debug 326169691Skan} // namespace std 327132720Skan 328132720Skan#endif 329