https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64816
Bug ID: 64816 Summary: gcc claims that constructor is private when it should be accessible Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: c++ Assignee: unassigned at gcc dot gnu.org Reporter: thakis at chromium dot org I came across this while trying to build chromium for android with libc++ and gcc. Here's an attempt at a reduction: $ cat repro2.cc namespace std { template <class _Iter> class __wrap_iter { private: __wrap_iter(_Iter __x) {} template <class _CharT> friend class basic_string; template <class _Tp> friend class vector; }; template <class _CharT> class basic_string { public: typedef const char *const_pointer; typedef __wrap_iter<const_pointer> const_iterator; const_iterator begin() const {return const_iterator(const_pointer(0));} }; typedef basic_string<char> string; template <class _Tp> class vector { public: typedef const _Tp *const_pointer; typedef __wrap_iter<const_pointer> const_iterator; const_iterator begin() const {return const_iterator(const_pointer(0));} }; } // namespace std void g(const std::vector<char> &v) { v.begin(); } # gcc doesn't like this (also broken in 4.4 and 4.9): $ gcc-4.8.1 -c repro2.cc gcc-4.8.1: warning: couldn’t understand kern.osversion ‘14.0.0 repro2.cc: In instantiation of ‘std::vector<_Tp>::const_iterator std::vector<_Tp>::begin() const [with _Tp = char; std::vector<_Tp>::const_iterator = std::__wrap_iter<const char*>]’: repro2.cc:30:46: required from here repro2.cc:5:3: error: ‘std::__wrap_iter<_Iter>::__wrap_iter(_Iter) [with _Iter = const char*]’ is private __wrap_iter(_Iter __x) {} ^ repro2.cc:25:71: error: within this context const_iterator begin() const {return const_iterator(const_pointer(0));} ^ It's true that the constructor is private, but vector is also a friend. clang likes it (icc too): $ bin/clang -c repro2.cc To make this more mysterious, gcc stops rejecting the problem if: 1.) I change `typedef const char *const_pointer;` to `typedef const _CharT *const_pointer;` 2.) or I declare `template <class _Tp> class vector;` before class __wrap_iter 3.) or I remove class basic_string (and typedef string) -- even though they aren't referenced anywhere.