Boost logo

Boost Users :

Subject: Re: [Boost-users] segfault using boost::thread_specific_ptr
From: Juan Ramírez (jramirez.uy_at_[hidden])
Date: 2015-12-21 14:07:15


yeah, sorry for that! I was writing from memory :P

On Mon, Dec 21, 2015 at 3:24 PM, Michael P. Soulier <
msoulier_at_[hidden]> wrote:

> Ah thanks. I had to change the check to if (! tls_buffer.get()) or
>
> In file included from ./EventWorker.h:13:
> ./Util.h:85:13: error: invalid argument type
> 'boost::thread_specific_ptr<std::stringstream>' to unary expression
> if (! tls_buffer) {
> ^ ~~~~~~~~~~
> 1 error generated.
> make: *** [EventWorker.o] Error 1
>
> but it seems to work now.
>
> Mike
>
> > On Dec 21, 2015, at 10:04 AM, Juan Ramírez <jramirez.uy_at_[hidden]>
> wrote:
> >
> > tls_buffer is not initialized, thread_specific_ptr will not allocate
> memory for you (it will call delete on thread exit tough)
> >
> > if (!tls_buffer) {
> > tls_buffer.reset(new std::stringstream());
> > }
> >
> > The previous must be done before any attempt to use that variable
> >
> > On Mon, Dec 21, 2015 at 11:34 AM, Michael P. Soulier <
> msoulier_at_[hidden]> wrote:
> > Hello,
> >
> > I’m trying to implement a thread-safe logger that uses a
> boost::thread_specific_ptr to a std::stringstream as a logging buffer.
> >
> > static boost::thread_specific_ptr<std::stringstream> tls_buffer;
> >
> > class MLoggerHandler
> > {
> > public:
> > MLoggerHandler(boost::mutex& mutex, std::ostream& ostream);
> > ~MLoggerHandler();
> > void setLevel(int level);
> >
> > template <class T>
> > // For handling << from any object.
> > MLoggerHandler& operator <<(T input) {
> > std::cerr << "Adding to buffer" << std::endl;
> > if (m_start) {
> > *tls_buffer << localDateTime() << " " << input;
> <================= SEGFAULT
> > m_start = false;
> > }
> > else {
> > *tls_buffer << input;
> > }
> > std::cerr << "On buffer: " << tls_buffer->str() << std::endl;
> > return *this;
> > }
> > // For handling std::endl
> > std::ostream& operator <<(std::ostream& (*f)(std::ostream&)) {
> > std::cerr << "Flushing buffer" << std::endl;
> > m_start = true;
> > std::ostream& rv = f(m_ostream);
> > m_mutex.lock();
> > m_ostream << tls_buffer->str();
> > m_mutex.unlock();
> > tls_buffer->str("");
> > return rv;
> > }
> > private:
> > // A flag to indicate the beginning of a new line.
> > bool m_start = true;
> > // A mutex passed in from the main logger for synchronization.
> > boost::mutex& m_mutex;
> > // The logging level.
> > int m_level;
> > // The output stream.
> > std::ostream& m_ostream;
> > // Return the current date and time as a localized string.
> > const std::string localDateTime();
> > };
> >
> > The initial idea, was to flush the buffer and write when a terminating
> std::endl was encountered. But, just trying to dereference the pointer and
> write to the std::stringstream is crashing. Do I need to initialize the
> std::stringstream, or is it initialized in constructor?
> >
> > Thanks,
> > Mike
> > _______________________________________________
> > Boost-users mailing list
> > Boost-users_at_[hidden]
> > http://lists.boost.org/mailman/listinfo.cgi/boost-users
> >
> >
> >
> > --
> > Juan
> > :wq
> >
> > _______________________________________________
> > Boost-users mailing list
> > Boost-users_at_[hidden]
> > http://lists.boost.org/mailman/listinfo.cgi/boost-users
>
> _______________________________________________
> Boost-users mailing list
> Boost-users_at_[hidden]
> http://lists.boost.org/mailman/listinfo.cgi/boost-users
>

-- 
Juan
:wq


Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net