views:

154

answers:

2

I'm getting memory allocation errors (and a subsequent crash) on the following simplified code:

std::wstring myKey = L"str_not_actually_constant";

MyType obj;
Read( obj );

std::map<std::wstring, MyType> myMap;
myMap[myKey] = obj; // Sometimes allocation error (1)
...
Read( MyType& obj )
{
  obj.member1 = ReadFromFuncThatMayBeProblem();
  obj.member2 = ReadFromFuncThatMayBeProblem(); // Sometimes allocation error (2)
  /* more members */
}
...
void operator =( const MyType& source )
{
  if( this != &source )
  {
    member1 = source.member1; // std::wstring
    member2 = source.member2; // Usually (1) happen on the second member. // std::wstring
    /* more members */
  }
}

Either (1) or (2) occur.

Now, if I simply continue on regardless of the error (with the debugger), the value is indeed entered in the map.

I don't know if ReadFromFuncThatMayBeProblem() is the culprit but it's a fairly complex function that I cannot devulge here.

Also, this is code that has worked (or at least appeared to work) before other sections of the application was ported to use OpenSSL. I don't know if that may have had any effect here, though.

So, what can I do to track down this allocation error, since I'm presuming that the above code is not in fact the problem?

Edit: More info: There is no dtor for MyType.

However, MyType has a member of type SecondType that has a void* member. This is being deleted and null'd in that type's destructor. The constructor uses m_pData = new std::wstring( ( (std::wstring )source.m_pData) ); for strings. (And similar for other data types). Could that be an issue? (delete static_cast< std::wstring* >( m_pData );)

The other member types of MyType are std::wstring, unsigned long, bool, enum, structs (timeb among them) and SecondType.

A: 

what type does ReadFromFuncThatMayBeProblem() return? Does it return a (const) reference? if so, is the object still valid after leaving the scope of ReadFromFuncThatMayBeProblem()?

nj
It returns whatever the type the member is (std::wstring, long etc). (Non-const.)
Fredrik Ullner
+1  A: 

Finally tracked down the error.

We are using the above functionality as part of a larger socket communication using OpenSSL (hence above reference). The socket was writing data and reading data as per above code simplification.

The way the socket was read was that we were re-allocating memory from one buffer to another (changing size dynamically). While doing this, we use the input of the buffer and the size we should expand with. The size calculation was using modulo to calculate the factor of the re-size. This caused the buffer to either be too large or too small to fit the following operations.

Two days of debugging to change a '%' to a '/'.

Thanks for all support, though.

Fredrik Ullner
I've a feeling you do not use assertions or much of logging. How do you plan to keep the code beast under your leash?
Amit Kumar
We are using assertions and logging. We simply didn't have anything like that in this case or in this particular part. It feels like you're trying to pick a fight...
Fredrik Ullner
+1 for simple error that requires a disproportionate effort to fix. Nice to know programming never changes at its core.
outis