Сергей Борщ 134 11 апреля, 2011 Опубликовано 11 апреля, 2011 · Жалоба Вроде бы по стандарту все понятно: class myclass { public: myclass() { тра-та-та } }; #include <new> void test() { myclass * Tmp = new(nothrow) myclass; if(!Tmp) { cout < "тра-та-та не удалось"; } } Но в реальности вижу, что независимо от возвращаемого new(size_t , nothrow_t) значения вызывается конструктор! А ведь new(nothrow) должен вернуть 0, если выделить память не удалось. Он и возвращает, а gcc молча вызывает конструктор с адресом объекта 0. known_message<decoded_message>* pElement = new(std::nothrow) known_message<decoded_message>(RSSI); if(pElement) { 107100: e3a0001c mov r0, #28 107104: e59f1068 ldr r1, [pc, #104]; 107174 <decoder::received(unsigned char)+0x84> 107108: eb00079b bl 108f7c <operator new(unsigned int, std::nothrow_t const&)> INLINE known_message(uint_fast8_t rssi) : raw_message(T::ID, sizeof(T), rssi) {} 10710c: e1a03007 mov r3, r7 107110: e3a01002 mov r1, #2 107114: e3a02008 mov r2, #8 107118: e1a05000 mov r5, r0 10711c: eb0002ca bl 107c4c <raw_message::raw_message(rf_message::id, unsigned int, unsigned int)> Что я упустил? IAR проверял и конструктор не вызывал. P.S. Код компилируется с -fno-exceptions. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
AHTOXA 15 11 апреля, 2011 Опубликовано 11 апреля, 2011 · Жалоба Хм. Проверил на простом gcc, для x86: class test_t { public: test_t() { std::cout << "\r\n in constructor"; } private: char arr[20]; }; void command_NTEST_handler(char*) { test_t * Tmp = new(std::nothrow) test_t; if(!Tmp) std::cout << "тра-та-та не удалось"; } скомпилилось в 0000000000401220 <command_NTEST_handler(char*)>: 401220: 48 83 ec 08 sub $0x8,%rsp 401224: be f0 22 60 00 mov $0x6022f0,%esi 401229: bf 14 00 00 00 mov $0x14,%edi 40122e: e8 4d f9 ff ff callq 400b80 <operator new(unsigned long, std::nothrow_t const&)@plt> 401233: 48 85 c0 test %rax,%rax 401236: 74 20 je 401258 <command_NTEST_handler(char*)+0x38> 401238: ba 11 00 00 00 mov $0x11,%edx 40123d: be 42 18 40 00 mov $0x401842,%esi 401242: bf e0 21 60 00 mov $0x6021e0,%edi 401247: e8 84 f9 ff ff callq 400bd0 <std::basic_ostream<char, std::char_traits<char> >& std::__ostream_insert<char, st Вроде скипается конструктор. Потом проверил на codesourcery g++ lite: class test_t { public: test_t() { uart << "\r\n in constructor"; } private: char arr[20]; }; void command_NTEST_handler(char*) { test_t * Tmp = new(std::nothrow) test_t; if(!Tmp) uart << "тра-та-та не удалось"; } Результат: 08000ff4 <command_NTEST_handler(char*)>: 8000ff4: f641 51b0 movw r1, #7600 ; 0x1db0 8000ff8: b510 push {r4, lr} 8000ffa: 2014 movs r0, #20 8000ffc: f6c0 0100 movt r1, #2048 ; 0x800 8001000: f000 f86e bl 80010e0 <operator new(unsigned int, std::nothrow_t const&)> 8001004: b180 cbz r0, 8001028 <command_NTEST_handler(char*)+0x34> Опять же, вроде есть проверка... Да, во втором случае используется нестандартный new, может это имеет значение. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 134 12 апреля, 2011 Опубликовано 12 апреля, 2011 · Жалоба Опять же, вроде есть проверка...Разобрался. Когда переопределял new для known_message не указал throw(). Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
liloukan 0 22 января, 2014 Опубликовано 22 января, 2014 · Жалоба Разобрался. Когда переопределял new для known_message не указал throw(). Извините, может не в тему: у меня есть проект Linux + QtGui на mips32. Для оптимизации по размеру пересобрал toolchain(gcc 4.3.6 + binutils 2.17 + eglibc-2.8) и SDK с опцией -fno-exceptions незначительно уменьшился размер libstdc++. Как по умолчанию сделать, чтобы new был std::nothrow? Toolchain не из buildroot, а самосборный с поддержкой --sysroot. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 134 22 января, 2014 Опубликовано 22 января, 2014 · Жалоба Как по умолчанию сделать, чтобы new был std::nothrow? Toolchain не из buildroot, а самосборный с поддержкой --sysroot. Не приходит в голову ничего кроме переопределния глобального operator new(size_t). Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
liloukan 0 22 января, 2014 Опубликовано 22 января, 2014 · Жалоба Не приходит в голову ничего кроме переопределния глобального operator new(size_t). Спасибо, так и сделаю. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться