Search

VS 2012 RC - std::thread reports memory leak (even on stack) by Greek Fire

Closed
as Fixed Help for as Fixed

4
0
Sign in
to vote
Type: Bug
ID: 757212
Opened: 8/6/2012 8:02:13 AM
Access Restriction: Public
0
Workaround(s)
0
User(s) can reproduce this bug
I noticed when using "crtdbg.h" to find memory leaks, the std::thread class, when run, always is reported as having a memory leak - even when on the stack.

I first had an array of thread objects on the heap and noticed the behaviour (even when deleting each individual thread and then the array of pointers). I then placed it on the stack and still had the memory leak reported.
Details (expand)

Visual Studio/Team Foundation Server/.NET Framework Tooling Version

Visual Studio 2012 RC

Steps to reproduce

I gave 3 scenarios that all report memory leaks below.

// ConsoleApplication1.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include <iostream>
#include <thread>
#include <vector>

#ifdef _DEBUG
    #define _CRTDBG_MAP_ALLOC
    #include <stdlib.h>
    #include <crtdbg.h>
    //#define new new(_NORMAL_BLOCK, __FILE__, __LINE__) when using std::thread, this line of code won't let it be compiled, if you have an answer to this as well I'd love to hear it
#endif

using namespace std;

class foo
{
    public:
        void write(int id)
        {
            for(int i = 0; i < 1000000000; i++)
            {
            }

            cout << id << endl;
        };
};

void print()
{
    cout << "p" << endl;
}

int _tmain(int argc, _TCHAR* argv[])
{
    {
        // all the below causes a memory leak to be reported

        // ARRAY ON HEAP EXAMPLE
        /*foo f[20];

        thread** t = new thread*[20];

        for(int i = 0; i < 20; i++)
            t[i] = new thread(&foo::write, f[i], i);

        for(int i = 0; i < 20; i++)
            t[i]->join();

        cout << "done" << endl;

        for(int i = 0; i < 20; i++)
        {
            cout << "DEL: " << i << endl;
            delete t[i];
        }

        delete[] t;*/

        // VECTOR of thread
        /*vector<thread> threads;

        for(int i = 0; i < 20; i++)
            threads.push_back(thread(print));

        for(int i = 0; i < 20; i++)
            threads[i].join();*/

        // single thread on stack
        thread t(print);
        t.join();
    }

    #ifdef _DEBUG
        _CrtDumpMemoryLeaks();
    #endif

    return 0;
}

Product Language

English

Operating System

Windows 7

Operating System Language

English

Actual results

In the output window for all 3 scenarios:

The thread 0x13dc has exited with code 0 (0x0).
Detected memory leaks!
Dumping objects ->
{247} normal block at 0x00505C50, 44 bytes long.
Data: <                > 01 00 00 00 00 00 00 00 00 00 00 00 0A 00 00 00
Object dump complete.
The thread 0x1260 has exited with code 0 (0x0).
The thread 0x9f4 has exited with code 0 (0x0).
The program '[3212] ConsoleApplication1.exe' has exited with code 0 (0x0).

Expected results

No reported memory leaks for any of the three scenarios described in the code above, in the main method.
File Attachments
0 attachments
Sign in to post a comment.
Posted by Microsoft on 12/17/2012 at 4:41 PM
Hi,

Thanks for reporting this bug. We've fixed it, and the fix will be available in the next release of our C++ Standard Library implementation.

Specifically, (1) we now clean up the at_thread_exit_mutex, and (2) we mark mutex (and condition_variable) allocations as "CRT blocks", which prevents them from being reported as memory leaks.

Note: Connect doesn't notify me about comments. If you have any further questions, please E-mail me.

Stephan T. Lavavej
Senior Developer - Visual C++ Libraries
stl@microsoft.com
Posted by Andreas Magnusson on 12/6/2012 at 2:36 AM
The leak is the "static _Mtx_t at_thread_exit_mutex" declared in "crt\src\thr\xnotify.c", which is allocated once for the first created std::thread but never freed. So it's not a leak per say, more of a "skipped cleaning up after me"-issue.

This is very undesirable since in our case we're failing our tests if a memory leak is detected. So for us, the first test to create a thread fails...not so good...

So the best fix IMHO would be to add an "atexit(destroy_at_thread_exit_mutex)" but only for debug builds (since we don't want it to take time in a release build when memory leaks aren't reported anyway and the memory will soon be freed anyhow).
Posted by Microsoft on 8/6/2012 at 7:39 PM
Thanks for your feedback.

We are rerouting this issue to the appropriate group within the Visual Studio Product Team for triage and resolution. These specialized experts will follow-up with your issue.
Posted by Microsoft on 8/6/2012 at 8:50 AM
Thank you for your feedback, we are currently reviewing the issue you have submitted. If this issue is urgent, please contact support directly(http://support.microsoft.com)
Sign in to post a workaround.