operator new: bad_alloc или NULL?
От: pavel_turbin  
Дата: 29.01.06 17:02
Оценка:
задумался на вопросом, что же на самом деле возвращает new когда не может выделить память?


в MSDN тут сказано

The new and delete Operators

In Visual C++ .NET 2002, the new function in the Standard C++ Library will support the behavior specified in the C++ standard,
which is to throw a std::bad_alloc exception if the memory allocation fails.


в том же MSDN сказано

Handling Insufficient Memory Conditions


Testing for failed memory allocation can be done with code such as the following:

// insufficient_memory_conditions.cpp
// compile with: /EHsc
#include <iostream>
using namespace std;
#define BIG_NUMBER 100000000
int main() {
int *pI = new int[BIG_NUMBER];
if( pI == 0x0 ) {
cout << "Insufficient memory" << endl;
return -1;
}
}


проверил, никакого bad_alloc exception не возникает, только NULL.

так что же должно вернуться из new, если не может выделить память?
Re: operator new: bad_alloc или NULL?
От: shank  
Дата: 29.01.06 17:15
Оценка:
Здравствуйте, pavel_turbin, Вы писали:

_>задумался на вопросом, что же на самом деле возвращает new когда не может выделить память?

18.4.1.1 Single-object forms
void* operator new(std::size_t size) throw(std::bad_alloc);
1 Effects: The allocation function (3.7.3.1) called by a new-expression (5.3.4) to allocate size bytes of
storage suitably aligned to represent any object of that size.
2 Replaceable: a C + + program may define a function with this function signature that displaces the default
version defined by the C + + Standard library.
3 Required behavior: Return a non-null pointer to suitably aligned storage (3.7.3), or else throw a
bad_alloc exception
. This requirement is binding on a replacement version of this function.
4 Default behavior:
— Executes a loop: Within the loop, the function first attempts to allocate the requested storage. Whether
the attempt involves a call to the Standard C library function malloc is unspecified.
— Returns a pointer to the allocated storage if the attempt is successful. Otherwise, if the last argument to
set_new_handler() was a null pointer, throw bad_alloc.
— Otherwise, the function calls the current new_handler (18.4.2.2). If the called function returns, the loop
repeats.
— The loop terminates when an attempt to allocate the requested storage is successful or when a called
new_handler function does not return.

Re[2]: operator new: bad_alloc или NULL?
От: pavel_turbin  
Дата: 29.01.06 17:20
Оценка:
Здравствуйте, shank, Вы писали:

S>Здравствуйте, pavel_turbin, Вы писали:


_>>задумался на вопросом, что же на самом деле возвращает new когда не может выделить память?

S>

S>18.4.1.1 Single-object forms
S>void* operator new(std::size_t size) throw(std::bad_alloc);
S>1 Effects: The allocation function (3.7.3.1) called by a new-expression (5.3.4) to allocate size bytes of
S>storage suitably aligned to represent any object of that size.
S>2 Replaceable: a C + + program may define a function with this function signature that displaces the default
S>version defined by the C + + Standard library.
S>3 Required behavior: Return a non-null pointer to suitably aligned storage (3.7.3), or else throw a
S>bad_alloc exception
. This requirement is binding on a replacement version of this function.


я тоже так думал пока не увидел, что "new char[0xffffffe]" выдает 0, никакого bad_alloc нет.
Re: operator new: bad_alloc или NULL?
От: korzhik Россия  
Дата: 29.01.06 17:24
Оценка:
Здравствуйте, pavel_turbin, Вы писали:

_>задумался на вопросом, что же на самом деле возвращает new когда не может выделить память?


[]

по стандарту, в случае неудачи, кидает std::bad_alloc.
Есть форма вызова возвращающая 0
#include <new>

  int* p = new (std::nothrow) int[BIG_NUMBER];
  if (p)
  {
  }


НО!
1. VC6 не кидает исключение и в случае неудачи возвращает 0 изменить это поведение можно здесь
Автор: korzhik
Дата: 10.06.05


2. Если используешь MFC, то надо учесть что MFC перекрывает new и кидает CMemoryException
Re[2]: operator new: bad_alloc или NULL?
От: pavel_turbin  
Дата: 29.01.06 17:32
Оценка:
Здравствуйте, korzhik, Вы писали:


K>НО!

K>1. VC6 не кидает исключение и в случае неудачи возвращает 0 изменить это поведение можно здесь
Автор: korzhik
Дата: 10.06.05


Спасибо! Это объясняет эффект. Кстати, отсутствие bad_alloc похоже справедливо и для VC2002, VC2005.
Re[3]: operator new: bad_alloc или NULL?
От: shank  
Дата: 29.01.06 17:32
Оценка:
Здравствуйте, pavel_turbin, Вы писали:

_>Здравствуйте, shank, Вы писали:


_>я тоже так думал пока не увидел, что "new char[0xffffffe]" выдает 0, никакого bad_alloc нет.


Так у вас VC6? Он не очень подходит, чтобы экспериментировать "как должно быть".
Re[4]: operator new: bad_alloc или NULL?
От: pavel_turbin  
Дата: 29.01.06 17:36
Оценка:
Здравствуйте, shank, Вы писали:

S>Здравствуйте, pavel_turbin, Вы писали:


_>>Здравствуйте, shank, Вы писали:


_>>я тоже так думал пока не увидел, что "new char[0xffffffe]" выдает 0, никакого bad_alloc нет.


S>Так у вас VC6? Он не очень подходит, чтобы экспериментировать "как должно быть".


нет я использую компилятор напрямую, без оболочки (WinDDK). CL+h+lib соответствует VC 2005.

ЗЫ.
Возврат 0 даже удобнее, чем bad_alloc, т.к. нет нужды связываться с исключениями.
Re[3]: operator new: bad_alloc или NULL?
От: korzhik Россия  
Дата: 29.01.06 17:36
Оценка:
Здравствуйте, pavel_turbin, Вы писали:

> Кстати, отсутствие bad_alloc похоже справедливо и для VC2002, VC2005.


не может быть.
Вот этот код кидает bad_alloc на VC7.1 (VC 2003)
#include <new>

int main( ) 
{
    using namespace std;
   try
   {
      while ( 1 ) 
      {
         int * p = new int[50000000];

         if (p)
            cout << "Allocating 50000000 ints.\n";
          else
          {
            cout << "return null\n";  
            break;
          }
      }
   }
   catch ( exception e )
   {
      cout << e.what( ) << endl;
   }
}
Re[4]: operator new: bad_alloc или NULL?
От: pavel_turbin  
Дата: 29.01.06 17:43
Оценка:
Здравствуйте, korzhik, Вы писали:

K>Здравствуйте, pavel_turbin, Вы писали:


>> Кстати, отсутствие bad_alloc похоже справедливо и для VC2002, VC2005.


K>не может быть.


возможно это из-за nothrownew.obj

If you still want the non-throwing version of new for the C Runtime Library, link your program with nothrownew.obj. However, when you link with nothrownew.obj, new in the Standard C++ Library will no longer function.
http://msdn2.microsoft.com/en-us/library/kftdy56f.aspx

Re[4]: operator new: bad_alloc или NULL?
От: vvotan Россия  
Дата: 30.01.06 11:47
Оценка:
Здравствуйте, korzhik, Вы писали:


K>не может быть.

K>Вот этот код кидает bad_alloc на VC7.1 (VC 2003)
А если убрать #include <new> , то не кидает
--
Sergey Chadov

... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.