unable to catch bad_alloc

classic Classic list List threaded Threaded
8 messages Options
Reply | Threaded
Open this post in threaded view
|

unable to catch bad_alloc

Palmer Eldritch
Copying from satck overflow : http://stackoverflow.com/questions/13851244/cant-catch-bad-alloc-in-mingw

See comments there - people suggest it is a mingw bug (the title was edited not by me)

COPY ---------------->
I am writing a program for a homework where I need to allocate many objects to check things on locality and performance etc. I can't seem to catch the exception thrown by `new`

    #include "List.h"
    #include<iostream>
    #include <exception>

    int main(int argc, char **argv) {
    cout << "size of List c++ : " << sizeof(List) << endl;  //16
    List * ptrList = new List();
    unsigned long var = 0;
    try {
    for (;; ++var) {
    List * ptrList2 = new  List();
    ptrList->next = ptrList2;
    ptrList2->previous = ptrList;
    ptrList = ptrList2;
    }
    } catch (bad_alloc const& e) {
    cout << "caught : " << e.what() << endl;
    // } catch (...) { //this won't work either
    }

Results in :

> This application has requested the Runtime to terminate it in an
> unusual way. Please contact the application's support team for more
> information.

If I change the allocation part as :


    List * ptrList2 = new (nothrow) List();
    if (!ptrList2) {
    cout << "out of memory - created " << var << " nodes" << endl;
    break;
    }

I get a nice :

    out of memory - created 87921929 nodes

Why can't I catch `bad_alloc` ?

I am on mingwin on Windows 7 x64 Pro

    C:\Users\MrD>g++ --version
    g++ (GCC) 4.7.2

The List :

    class List {
    long j;
    public:
    List * next;
    List * previous;
    virtual long jj() {
    return this->j;
    }
    List() {
    next = previous = 0;
    j = 0;
    }
    virtual ~List() {
    if (next) {
    next->previous = this->previous;
    }
    if (previous) {
    previous->next = this->next;
    }
    }
    };


Reply | Threaded
Open this post in threaded view
|

Re: unable to catch bad_alloc

Keith Marshall
On 13/12/12 14:24, Palmer Eldritch wrote:
> I am writing a program for a homework where I need to allocate many objects
> to check things on locality and performance etc. I can't seem to catch the
> exception thrown by `new`
>
>      #include "List.h"

Since you neglected to show us your List class declaration, I had to
provide my own.

>      #include<iostream>
>      #include <exception>
>
>      int main(int argc, char **argv) {
>       cout << "size of List c++ : " << sizeof(List) << endl;  //16
>       List * ptrList = new List();
>       unsigned long var = 0;
>       try {
>       for (;; ++var) {
>       List * ptrList2 = new  List();
>       ptrList->next = ptrList2;
>       ptrList2->previous = ptrList;
>       ptrList = ptrList2;

Since this is a homework question, I will not show you my solution,
but if this is indicative of your class design, I would feel very
generous if I gave you 3/10 for it.  Anyway, after adapting this to my
own class design, and fixing the bugs which mean that your code should
not even compile, let alone run to an uncaught exception...

>       }
>       } catch (bad_alloc const& e) {
>       cout << "caught : " << e.what() << endl;

...this works perfectly for me, both with mingw32-g++ v4.5.2 on my Vista
box at work, and with v4.7.2 on my Win7 VM at home; i.e., with the cout
modified to:

   cout << e.what() << " after allocating " << var << " nodes.\n";

I (eventually) see:

   std::bad_alloc after allocating 1948534 nodes.

(the count may vary depending on the amount of available free heap
memory, and the relative sizes of our respective List objects, but this
is exactly as I would expect, when the exception is caught.

>      // } catch (...) { //this won't work either
>       }

I even enabled this, but it wasn't needed, because the preceding catch
succeeded; I have no reason to expect that this would not work, if the
exception hadn't been caught otherwise.

--
Regards,
Keith.

------------------------------------------------------------------------------
LogMeIn Rescue: Anywhere, Anytime Remote support for IT. Free Trial
Remotely access PCs and mobile devices and provide instant support
Improve your efficiency, and focus on delivering more value-add services
Discover what IT Professionals Know. Rescue delivers
http://p.sf.net/sfu/logmein_12329d2d
_______________________________________________
MinGW-users mailing list
[hidden email]

This list observes the Etiquette found at
http://www.mingw.org/Mailing_Lists.
We ask that you be polite and do the same.  Disregard for the list etiquette may cause your account to be moderated.

_______________________________________________
You may change your MinGW Account Options or unsubscribe at:
https://lists.sourceforge.net/lists/listinfo/mingw-users
Also: mailto:[hidden email]?subject=unsubscribe
Reply | Threaded
Open this post in threaded view
|

Re: unable to catch bad_alloc

Palmer Eldritch


On Thu, Dec 13, 2012 at 9:45 PM, Keith Marshall [via MinGW-users] <[hidden email]> wrote:
>
> On 13/12/12 14:24, Palmer Eldritch wrote:
> > I am writing a program for a homework where I need to allocate many objects
> > to check things on locality and performance etc. I can't seem to catch the
> > exception thrown by `new`
> >
> >      #include "List.h"
>
> Since you neglected to show us your List class declaration, I had to
> provide my own.

 
My list declaration **is** in my email ?!?
The List :

    class List {
    long j;//etc
    };

Please read carefully.
 
>
>
> >      #include<iostream>
> >      #include <exception>
> >
> >      int main(int argc, char **argv) {
> >       cout << "size of List c++ : " << sizeof(List) << endl;  //16
> >       List * ptrList = new List();
> >       unsigned long var = 0;
> >       try {
> >       for (;; ++var) {
> >       List * ptrList2 = new  List();
> >       ptrList->next = ptrList2;
> >       ptrList2->previous = ptrList;
> >       ptrList = ptrList2;
>
> Since this is a homework question, I will not show you my solution,
> but if this is indicative of your class design, I would feel very
> generous if I gave you 3/10 for it.  Anyway, after adapting this to my
> own class design, and fixing the bugs which mean that your code should
> not even compile, let alone run to an uncaught exception...

 
My code did compile and run and if you mean having public fields and the like this was by design. And I started breaking things to pin this particular issue
I urge you to see the link in Stack overflow and the comments there - I made clear there are relevant pieces of information there
I allocated around 87921929 nodes (varying from execution to execution) and maybe the "bug" (I was *told* it was probably a bug in SO) has to do with the (rather huge) number of objects created

In SO someone posted a snippet in http://ideone.com/YN6we4

I reproduce the snippet here - if you can spot a bug in my code that might lead to this behavior then the case is closed:

// ******BEGIN FILE : ideone.com.YN6we4.cpp

class List {
    long j;
public:
    List * next;
    List * previous;
    virtual long jj() {
        return this->j;
    }
    List() {
        next = previous = 0;
        j = 0;
    }
    virtual ~List() {
        if (next) {
            next->previous = this->previous;
        }
        if (previous) {
            previous->next = this->next;
        }
    }
};
 
#include <iostream>
#include <exception>
using namespace std;
 
int main(int argc, char **argv) {
    cout << "size of List c++ : " << sizeof(List) << endl;  //16
    List * ptrList = new List();
    unsigned long var = 0;
    try {
        for (;; ++var) {
            List * ptrList2 = new  List();
            ptrList->next = ptrList2;
            ptrList2->previous = ptrList;
            ptrList = ptrList2;
        }
    } catch (bad_alloc const& e) {
        cout << "caught : " << e.what() << endl;
//  } catch (...) { //this won't work either
    }
}

// ******END FILE: ideone.com.YN6we4.cpp

When I compile and run this I get the crash :


C:\Users\MrD\Desktop\mingw bug>g++ ideone.com.YN6we4.cpp

C:\Users\MrD\Desktop\mingw bug>a.exe
size of List c++ : 16

This application has requested the Runtime to terminate it in an unusual way.
Please contact the application's support team for more information.


C:\Users\MrD\Desktop\mingw bug>g++ --version
g++ (GCC) 4.7.2
Copyright (C) 2012 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.


C:\Users\MrD\Desktop\mingw bug>


Did I say thanks for your time ? :)

Btw feel free to post your solution - the deadline expired and it was a bonus anyway :)

Also
>
>
> >       }
> >       } catch (bad_alloc const& e) {
> >       cout << "caught : " << e.what() << endl;
>
> ...this works perfectly for me, both with mingw32-g++ v4.5.2 on my Vista
> box at work, and with v4.7.2 on my Win7 VM at home; i.e., with the cout
> modified to:
>
>    cout << e.what() << " after allocating " << var << " nodes.\n";
>
> I (eventually) see:
>
>    std::bad_alloc after allocating 1948534 nodes.
>
> (the count may vary depending on the amount of available free heap
> memory, and the relative sizes of our respective List objects, but this
> is exactly as I would expect, when the exception is caught.
>
> >      // } catch (...) { //this won't work either
> >       }
>
> I even enabled this, but it wasn't needed, because the preceding catch
> succeeded; I have no reason to expect that this would not work, if the
> exception hadn't been caught otherwise.
>
> --
> Regards,
> Keith.
>
> ------------------------------------------------------------------------------
> LogMeIn Rescue: Anywhere, Anytime Remote support for IT. Free Trial
> Remotely access PCs and mobile devices and provide instant support
> Improve your efficiency, and focus on delivering more value-add services
> Discover what IT Professionals Know. Rescue delivers
> http://p.sf.net/sfu/logmein_12329d2d
> _______________________________________________
> MinGW-users mailing list
> [hidden email]
>
> This list observes the Etiquette found at
> http://www.mingw.org/Mailing_Lists.
> We ask that you be polite and do the same.  Disregard for the list etiquette may cause your account to be moderated.
>
> _______________________________________________
> You may change your MinGW Account Options or unsubscribe at:
> https://lists.sourceforge.net/lists/listinfo/mingw-users
> Also: mailto:[hidden email]?subject=unsubscribe
>
>
> ________________________________
> If you reply to this email, your message will be added to the discussion below:
> http://mingw-users.1079350.n2.nabble.com/unable-to-catch-bad-alloc-tp7579725p7579730.html
> To unsubscribe from unable to catch bad_alloc, click here.
> NAML

Reply | Threaded
Open this post in threaded view
|

Re: unable to catch bad_alloc

George Koehler
In reply to this post by Palmer Eldritch
"This application has requested the Runtime to terminate it in an
unusual way. Please contact the application's support team for more
information."

This happens when something calls abort().

I put your code in badm.cc (see attachment) and reproduced your problem.
I used g++ 4.7.2 with Windows 7. Here's the backtrace from gdb:

$ g++ -o badm badm.cc
$ gdb badm
GNU gdb (GDB) 7.5
...
(gdb) break abort
Breakpoint 1 at 0x401dd8
(gdb) run
Starting program: c:\Users\Kernigh\Documents\Code\badm.exe
[New Thread 436.0x168]
size of List c++ : 16

Breakpoint 1, 0x76a28e76 in msvcrt!abort ()
    from C:\Windows\syswow64\msvcrt.dll
(gdb) bt
#0  0x76a28e76 in msvcrt!abort () from C:\Windows\syswow64\msvcrt.dll
#1  0x6e9577dc in libgcc_s_dw2-1!__gcc_personality_v0 ()
    from C:\MinGW\bin\libgcc_s_dw2-1.dll
(gdb)

So libgcc_s_dw-1.dll calls abort(), but I don't know why. My
libgcc_s_dw-1.dll seems to have no debugger info. I believe that
libgcc_s_dw2-1.dll is the compiler's support library. The "dw2" might
refer to DWARF2-style exceptions.

The problem only happens with Windows. When I compiled the same code for
OpenBSD (not Windows), it worked:
size of List c++ : 32
caught : std::bad_alloc

--George Koehler

------------------------------------------------------------------------------
LogMeIn Rescue: Anywhere, Anytime Remote support for IT. Free Trial
Remotely access PCs and mobile devices and provide instant support
Improve your efficiency, and focus on delivering more value-add services
Discover what IT Professionals Know. Rescue delivers
http://p.sf.net/sfu/logmein_12329d2d
_______________________________________________
MinGW-users mailing list
[hidden email]

This list observes the Etiquette found at
http://www.mingw.org/Mailing_Lists.
We ask that you be polite and do the same.  Disregard for the list etiquette may cause your account to be moderated.

_______________________________________________
You may change your MinGW Account Options or unsubscribe at:
https://lists.sourceforge.net/lists/listinfo/mingw-users
Also: mailto:[hidden email]?subject=unsubscribe

badm.cc (831 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: unable to catch bad_alloc

Palmer Eldritch
This post was updated on .
In reply to this post by Keith Marshall
EDIT :
@George Koehler : thanks for saving my sanity :) The issue is too technical for me - I will try to follow up though- I knew about abort()

the reply below was @Keith Marshall :
Just to add that when I replace the line :

            List * ptrList2 = new  List();


in ideone.com.YN6we4.cpp with :

            List * ptrList2 = new (nothrow) List();
            if (!ptrList2) {
                        cout << "out of memory - created " << var << "
nodes" << endl;
                        break;
             }

I get :

C:\Users\MrD\Desktop\mingw bug>g++ ideone.com.YN6we4.cpp

C:\Users\MrD\Desktop\mingw bug>a.exe
size of List c++ : 16
out of memory - created 87929614 nodes

C:\Users\MrD\Desktop\mingw bug>

I have 6 GB of RAM, on a i7 950, Windows x64 7 Pro

So why is this happening?
Reply | Threaded
Open this post in threaded view
|

Re: unable to catch bad_alloc

George Koehler
In reply to this post by George Koehler
This program reproduces the problem:

#include <iostream>
#include <exception>

int main() {
   try {
     for (;;)
       new char[128];
   } catch (std::bad_alloc const& e) {
     std::cout << "caught : " << e.what() << std::endl;
   }
   return 0;
}

If I use new char[256], the program catches std::bad_alloc, as I expect.
If I use new char[128], the program aborts with this message:

 > This application has requested the Runtime to terminate it in an
unusual way.
 > Please contact the application's support team for more information.

The gdb backtrace looks different now:

 > Breakpoint 1, 0x75f98e76 in msvcrt!abort ()
 >    from C:\Windows\syswow64\msvcrt.dll
 > (gdb) bt
 > #0  0x75f98e76 in msvcrt!abort() from C:\Windows\syswow64\msvcrt.dll
 > #1  0x6e9579ee in libgcc_s_dw2-1!__emutls_get_address ()
 >    from C:\MinGW\bin\libgcc_s_dw2-1.dll
 > #2  0x77781bd1 in ntdll!RtlDisableThreadProfiling ()
 >    from C:\Windows\system32\ntdll.dll
 > #3  0x77739bfa in ntdll!AlpcMaxAllowedMessageLength ()
 >    from C:\Windows\system32\ntdll.dll
 > #4  0x00520000 in ?? ()
 > Backtrace stopped: previous frame inner to this frame (corrupt stack?)
 > (gdb)

This happened with Windows 7 and g++ 4.7.2.

------------------------------------------------------------------------------
LogMeIn Rescue: Anywhere, Anytime Remote support for IT. Free Trial
Remotely access PCs and mobile devices and provide instant support
Improve your efficiency, and focus on delivering more value-add services
Discover what IT Professionals Know. Rescue delivers
http://p.sf.net/sfu/logmein_12329d2d
_______________________________________________
MinGW-users mailing list
[hidden email]

This list observes the Etiquette found at
http://www.mingw.org/Mailing_Lists.
We ask that you be polite and do the same.  Disregard for the list etiquette may cause your account to be moderated.

_______________________________________________
You may change your MinGW Account Options or unsubscribe at:
https://lists.sourceforge.net/lists/listinfo/mingw-users
Also: mailto:[hidden email]?subject=unsubscribe
Reply | Threaded
Open this post in threaded view
|

Re: unable to catch bad_alloc

Earnie Boyd
On Tue, Dec 18, 2012 at 3:16 PM, George Koehler wrote:
> This program reproduces the problem:
>

I suspect the issue to be multiple runtime boundary crossing.  Does
your sample work as expected with -static-stdlibc++ added to the build
command?

--
Earnie
-- https://sites.google.com/site/earnieboyd

------------------------------------------------------------------------------
LogMeIn Rescue: Anywhere, Anytime Remote support for IT. Free Trial
Remotely access PCs and mobile devices and provide instant support
Improve your efficiency, and focus on delivering more value-add services
Discover what IT Professionals Know. Rescue delivers
http://p.sf.net/sfu/logmein_12329d2d
_______________________________________________
MinGW-users mailing list
[hidden email]

This list observes the Etiquette found at
http://www.mingw.org/Mailing_Lists.
We ask that you be polite and do the same.  Disregard for the list etiquette may cause your account to be moderated.

_______________________________________________
You may change your MinGW Account Options or unsubscribe at:
https://lists.sourceforge.net/lists/listinfo/mingw-users
Also: mailto:[hidden email]?subject=unsubscribe
Reply | Threaded
Open this post in threaded view
|

Re: unable to catch bad_alloc

George Koehler
On 12/19/2012 1:59 PM, Earnie Boyd wrote:
> I suspect the issue to be multiple runtime boundary crossing. Does
> your sample work as expected with -static-stdlibc++ added to the build
> command?

I guess you meant -static-libstdc++.

It doesn't help. I compiled my sample (the one with new char[128]) with,
$ g++ -o badm2 badm2.cc -static-libstdc++

but ./badm2 still aborts with the "This application has requested..."
message.

------------------------------------------------------------------------------
LogMeIn Rescue: Anywhere, Anytime Remote support for IT. Free Trial
Remotely access PCs and mobile devices and provide instant support
Improve your efficiency, and focus on delivering more value-add services
Discover what IT Professionals Know. Rescue delivers
http://p.sf.net/sfu/logmein_12329d2d
_______________________________________________
MinGW-users mailing list
[hidden email]

This list observes the Etiquette found at
http://www.mingw.org/Mailing_Lists.
We ask that you be polite and do the same.  Disregard for the list etiquette may cause your account to be moderated.

_______________________________________________
You may change your MinGW Account Options or unsubscribe at:
https://lists.sourceforge.net/lists/listinfo/mingw-users
Also: mailto:[hidden email]?subject=unsubscribe