Template Class Error

Go To Last Post
6 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I have been using Atmel Studio for years but I have no experience with Template Classes.  I am using some STL items and they have compiled fine in the past.  I recently had need to install a new system drive and a fresh install of Windows 10, Atmel Studio (7.0.2397), etc.  When I went to compile my (ATMega1284) solution I got the following error:

 

default argument for template parameter for class enclosing 'class std::basic_istream<charT, traits>::sentry'

 

[File/line was: C:\Users\misc\Dropbox\Signals\Firmware\WorkingCopies\BC002 Dev (Trunk)\AVR STL Library\avr-stl\include\istream    343]

 

I am not sure where I got this copy of STL (thus what version it is) but the istream header is:

/*	Copyright (C) 2004 Garrett A. Kajmowicz

	This file is part of the uClibc++ Library.

	This library is free software; you can redistribute it and/or
	modify it under the terms of the GNU Lesser General Public
	License as published by the Free Software Foundation; either
	version 2.1 of the License, or (at your option) any later version.

	This library is distributed in the hope that it will be useful,
	but WITHOUT ANY WARRANTY; without even the implied warranty of
	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
	Lesser General Public License for more details.

	You should have received a copy of the GNU Lesser General Public
	License along with this library; if not, write to the Free Software
	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
*/

 

These are the lines it is complaining about with the error cursor on line 343 (first line) between the "::" and "sentry":


	template <class charT,class traits = char_traits<charT> > class _UCXXEXPORT basic_istream<charT,traits>::sentry {
		bool ok;
	public:
		explicit _UCXXEXPORT sentry(basic_istream<charT,traits>& os, bool noskipws = false){
			if(os.good() !=0){		//Prepare for output
			}

			//Flush any tied buffer
			if(os.tie() != 0){
				os.tie()->flush();
			}
			if(!noskipws){
				__skipws(os);
			}

			ok = true;
		}
		_UCXXEXPORT ~sentry() { }
		_UCXXEXPORT operator bool() {
			return ok;
		}
	};

For completeness, it is also complaining with the same error on this code on line 281 at "sentry":

	template <class charT,class traits = char_traits<charT> >
		class _UCXXEXPORT basic_ostream<charT,traits>::sentry
	{
		bool ok;
	public:
		explicit _UCXXEXPORT sentry(basic_ostream<charT,traits>& os): ok(true){
			if(os.good() !=0){		//Prepare for output
			}

			//Flush any tied buffer
			if(os.tie() !=0 ){
				os.tie()->flush();
			}
		}
		_UCXXEXPORT ~sentry() { }
		_UCXXEXPORT operator bool() {
			return ok;
		}
	};

This is the same solution, project file, etc. (SVN checkout ... and STL library) that compiles correctly on the old system hard drive so I assume that it has to do with some Atmel Studio parameter/package that is global to Atmel Studio rather than the solution/project.

 

Let me know if more information is needed.

 

Thanks in advance for any assistance you might be able to offer.

 

Chuck Hackett

This topic has a solution.
Last Edited: Mon. Apr 6, 2020 - 01:10 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I just verified that this solution compiles on another system with Atmel Studio 7.0.1417

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

More info: 

 

1) The toolchain on the other computer which compiles successfully is avr8-gnu-toolchain-3.5.4.1709 (as identified by the release notes PDF in the avr8\avr8-gnu-toolchain folder)

2) The toolchain on the computer which does not compile successfully is avr8-gnu-toolchain-3.6.2.1778

3) I installed 3.5.4.1709 on the failing machine as a separate toolchain 'flavour' and the solution now compiles successfully.

 

Can anyone help me identify exactly what the new toolchain does not like about the STL file above so that I can return to the 'native' toolchain?

 

Regards,

Chuck Hackett

This reply has been marked as the solution. 
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The definition that you provided is a definition of a nested class `sentry` previously declared inside an enclosing class template `basic_istream<charT,traits>`. When making a definition of such nested class outside of its "owner" template, it is not legal to repeat the default arguments of the owner template.

 

Here's a minimal reproduction of the same problem 

 

template <typename T = int> struct S
{
  struct U;
};

template <typename T = int> struct S<T>::U // Error: you are not supposed to specify the default argument here
{
};

The above code will produce the same error, because it re-states a default argument that has already been stated above. Remove the second occurrence of the default argument and the code will compile.

 

template <typename T = int> struct S
{
  struct U;
};

template <typename T> struct S<T>::U // No problems here
{
};

 

The very same rule applies to all template member definitions made outside the "owning" class template definition

 

template <typename T = int> class S
{
  void foo();
};

template <typename T = int> void S<T>::foo() // Error: you are not supposed to specify the default argument here
{
}

A quick experiment on Godbolt shows that GCC failed to detect this error in GCC 4 era. Starting from GCC 5 this error is caught and reported. Apparently, your standard library implementation hails from those dark ages. So, it is expected that AVR-GCC toolchain based on GCC 4 codebase will accept that library implementation, while later versions should complain.

Last Edited: Mon. Apr 6, 2020 - 03:00 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

He has two threads going.

 

https://www.avrfreaks.net/commen...

 

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

AndreyT wrote:
The definition that you provided is a definition of a nested class `sentry` previously declared inside an enclosing class template `basic_istream<charT,traits>`. When making a definition of such nested class outside of its "owner" template, it is not legal to repeat the default arguments of the owner template.

 

THANK YOU !!!

 

I removed the offending re-declaration of the default arguments.

 

I then compared the hex output produced by the old avr-gcc compiling the old and new STL code and they were identical … thus confirming that the change generated the same code as the original.

 

I then compiled the solution with the native (latest) avr-gcc and it compiled successfully.  The generated code was smaller but, for the moment, I assume that this difference is due to avr-gcc compiler improvements.  I still have to verify that the firmware works correctly but I am hopeful.

 

For those interested, I found where I documented where I got this STL library and it was from here:

https://andybrown.me.uk/downloads/

 

AndreyT:  Thanks Again !

 

Regards,

Chuck Hackett