Modify

#11998 closed Bugs (fixed)

Static const variables cannot be logged

Reported by: Hendrik Schall <torres@…> Owned by: Andrey Semashev
Milestone: To Be Determined Component: log
Version: Boost 1.60.0 Severity: Problem
Keywords: log static const Cc:

Description

Static const variables cannot be logged for me any more. I am using RHEL 7.1 and the Intel icpc for my programms (boost compiled with gcc 4.8.3)

The following code does not work in 1.60.0 but does in 1.59.0 Maybe it has to do with the changes regarding formatting_ostream #11549 or #11545

Code:

/* 
 * File:   main.cpp
 * Author: hschall
 *
 * Created on February 18, 2016, 6:53 AM
 */

#include <cstdlib>
#define BOOST_LOG_DYN_LINK
#include <boost/log/trivial.hpp>

class TestStaticError{
    public:
        static void doLog(){
          BOOST_LOG_TRIVIAL(debug) << myVar;
        }
    private:
        static const unsigned int myVar = 1337;
};

class TestStaticWorking{
    public:
        static void doLog(){
            BOOST_LOG_TRIVIAL(debug) << (unsigned int)myVar;
        }
    private:
        static const unsigned int myVar = 1337;
};

using namespace std;

/*
 * 
 */
int main(int argc, char** argv){

  TestStaticWorking::doLog(); // Works
  
  // Works in 1.59.0
  //TestStaticError::doLog(); // main.cpp:21: undefined reference to `TestStaticError::myVar' 
  
  return 0;
}

Attachments (0)

Change History (4)

comment:1 Changed 21 months ago by Andrey Semashev

I don't think this is a bug in the library.

The static constant members have to be defined in some (one) translation unit, which gives them storage. In C++11 and later this is required if a reference to the variable is taken, which happens when you call the operator<<. In pre-C++11 versions of the language, IIRC, the definition is required unconditionally.

The type conversion that you use as a workaround makes the operator<< bind the reference to a temporary, that's why it works. I'm not sure how it works differently in 1.59 since I don't see any changes that could lead to that but there were such changes since 1.58 - the operator<< overloads could have been chosen differently before, which would result in not taking the reference.

However, I can see that your use case could be useful, and I'll see if I can support it in the future.

comment:2 Changed 21 months ago by Hendrik Schall <torres@…>

The workaround is just to show that this behaviour relates to the static variable.

I compile with C++11 (but tested it also with C++98 and C++14). I did test it with the GCC (4.8.3) now aswell, same behaviour.

Wether it is a bug or not, it depends on the boost library version, which is strange.

comment:3 Changed 14 months ago by o.z

I see similar problem using bitfields:

I took the example from http://www.boost.org/doc/libs/1_61_0/libs/log/example/doc/tutorial_trivial_flt.cpp and added a bitfield print:

#include <boost/log/core.hpp>
#include <boost/log/trivial.hpp>
#include <boost/log/expressions.hpp>

namespace logging = boost::log;

//[ example_tutorial_trivial_with_filtering
void init()
{
    logging::core::get()->set_filter
    (
        logging::trivial::severity >= logging::trivial::info
    );
}


struct BF {
                unsigned int b : 8;
                BF() : b(0) {}
};


int main(int, char*[])
{
    init();

    BF bf;
    BOOST_LOG_TRIVIAL(info) << "An informational severity message " << bf.b;

    return 0;
}
//]

With boost 1.60 I got a compilation error:

cannot bind bitfield 'bf.BF::b' to 'unsigned int&'

With boost 1.57 the code is compiled and run (prints: [2016-09-19 20:21:33.018112] [0x000007fd1d5be672] [info] An informational severity message 0)

comment:4 Changed 14 months ago by Andrey Semashev

Resolution: fixed
Status: newclosed

Modify Ticket

Change Properties
Set your email in Preferences
Action
as closed The owner will remain Andrey Semashev.
The resolution will be deleted.

Add Comment


E-mail address and name can be saved in the Preferences.

 
Note: See TracTickets for help on using tickets.