Question

I'm a student, and my Operating Systems class project has a little snag, which is admittedly a bit superfluous to the assignment specifications itself:

While I can push 1 million deques into my deque of deques, I cannot push ~10 million or more.

Now, in the actual program, there is lots of stuff going on, and the only thing already asked on Stack Overflow with even the slightest relevance had exactly that, only slight relevance. https://stackoverflow.com/a/11308962/3407808

Since that answer had focused on "other functions corrupting the heap", I isolated the code into a new project and ran that separately, and found everything to fail in exactly the same ways.

Here's the code itself, stripped down and renamed for the sake of space.

#include <iostream>
#include <string>
#include <sstream>
#include <deque>

using namespace std;

class cat

{
    cat();
};

bool number_range(int lower, int upper, double value)
{
    while(true)
    {
        if(value >= lower && value <= upper)
        {
            return true;
        }
        else
        {
            cin.clear();
            cerr << "Value not between " << lower << " and " << upper << ".\n";
            return false;
        }
    }
}

double get_double(char *message, int lower, int upper)
{

    double out;
    string in;

    while(true) {

        cout << message << " ";
        getline(cin,in);
        stringstream ss(in); //convert input to stream for conversion to double

        if(ss >> out && !(ss >> in))
        {
            if (number_range(lower, upper, out))
            {
                return out;
            }
        }
        //(ss >> out) checks for valid conversion to double
        //!(ss >> in) checks for unconverted input and rejects it

        cin.clear();
        cerr << "Value not between " << lower << " and " << upper << ".\n";
    }
}

int main()
{
    int dq_amount = 0;
    deque<deque <cat> > dq_array;
    deque<cat> dq;

    do {
        dq_amount = get_double("INPUT # OF DEQUES: ", 0, 99999999);
        for (int i = 0; i < number_of_printers; i++)
        {
            dq_array.push_back(dq);
        }
    } while (!number_range(0, 99999999, dq_amount));
}

In case that's a little obfuscated, the design (just in case it's related to the error) is that my program asks for you to input an integer value. It takes your input and verifies that it can be read as an integer, and then further parses it to ensure it is within certain numerical bounds. Once it's found within bounds, I push deques of myClass into a deque of deques of myClass, for the amount of times equal to the user's input.

This code has been working for the past few weeks that I've being making this project, but my upper bound had always been 9999, and I decided to standardize it with most of the other inputs in my program, which is an appreciably large 99,999,999. Trying to run this code with 9999 as the user input works fine, even with 99999999 as the upper bound. The issue is a runtime error that happens if the user input is 9999999+.

Is there any particular, clear reason why this doesn't work?

Oh, right, the error message itself from Code::Blocks 13.12:

terminate called after throwing an instance of 'std::bad_alloc'

what(): std::bad_alloc

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

Process returned 3 (0x3) execution time : 12.559 s Press any key to continue.

I had screenshots, but I need to be 10+ reputation in order to put images into my questions.

Was it helpful?

Solution

This looks like address space exhaustion.

If you are compiling for a 32-bit target, you will generally be limited to 2 GiB of user-mode accessible address space per process, or maybe 3 GiB on some platforms. (The remainder is reserved for kernel-mode mappings shared between processes)

If you are running on a 64-bit platform and build a 64-bit binary, you should be able to do substantially more new/alloc() calls, but be advised you may start hitting swap.

Alternatively, you might be hitting a resource quota even if you are building a 64-bit binary. On Linux you can check ulimit -d to see if you have a per-process memory limit.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top