std::fopen падает в релизе с ошибкой 0xc0000417
От: удусекшл  
Дата: 03.02.22 13:53
Оценка:
Здравствуйте!

Такой код:
    if (!appConfig.outputFilename.empty())
    {
        std::string openMode = "w";
        if (!appConfig.getOptOverwrite())
            openMode.append("x"); // This flag forces the function to fail if the file exists, instead of overwriting it.


        cout<<"try to create file '" << appConfig.outputFilename << "', open mode: '" << openMode << "'" << endl;

        errno = 0;
        std::FILE* pFile = std::fopen( appConfig.outputFilename.c_str(), openMode.c_str() );

        //...
    }


В ouput отладчика прилетает:

try to create file 'test.txt', open mode: 'wx'
The thread 0x4730 has exited with code -1073740777 (0xc0000417).
// Тут ёще куча потоков с тем же кодом завершается


std::fopen принимает в обоих параметрах const char* — вроде всё легально. Значения я печатаю до вызова — и имя файла и openMode — валидные строки.

В Debug сборке всё работает без нареканий. Я видимо, где-то протупил, но не пойму где.



ЗЫ std::fopen нужна вообще только с одной целью — обломаться, если файл существует. Почему-то стандартные потоки не имеют такого флага
Re: std::fopen падает в релизе с ошибкой 0xc0000417
От: Pavel Dvorkin Россия  
Дата: 03.02.22 13:59
Оценка:
Здравствуйте, удусекшл, Вы писали:

У> openMode.append("x"); // This flag forces the function to fail if the file exists, instead of overwriting it.



Какая версия C++ ? Выделено мной — PD

File access mode flag "x" can optionally be appended to "w" or "w+" specifiers. This flag forces the function to fail if the file exists, instead of overwriting it. (C++17)

https://en.cppreference.com/w/cpp/io/c/fopen
With best regards
Pavel Dvorkin
Re: std::fopen падает в релизе с ошибкой 0xc0000417
От: reversecode google
Дата: 03.02.22 14:02
Оценка:
std filesystem уже сто лет в обед завезли

https://stackoverflow.com/questions/55138498/how-can-i-debug-the-cause-of-a-0xc0000417-exit-code
exit error code 0xc0000417 (which translates to STATUS_INVALID_CRUNTIME_PARAMETER)

windbg запустите и он все расскажет
Re[2]: std::fopen падает в релизе с ошибкой 0xc0000417
От: удусекшл  
Дата: 03.02.22 14:02
Оценка:
Здравствуйте, Pavel Dvorkin, Вы писали:

PD>Какая версия C++ ? Выделено мной — PD


PD>File access mode flag "x" can optionally be appended to "w" or "w+" specifiers. This flag forces the function to fail if the file exists, instead of overwriting it. (C++17)


PD>https://en.cppreference.com/w/cpp/io/c/fopen



MSVC с ключиком "ISO C++17 Standard (/std:c++17)"
Re: std::fopen падает в релизе с ошибкой 0xc0000417
От: LaptevVV Россия  
Дата: 03.02.22 14:22
Оценка:
1. Явно падает по неправильному указателю. Скорее всего нулевой.
2. В С++17 есть уже файловая система, и там уже есть что-то вроде exist() для файла.
Хочешь быть счастливым — будь им!
Без булдырабыз!!!
Re[2]: std::fopen падает в релизе с ошибкой 0xc0000417
От: удусекшл  
Дата: 03.02.22 14:30
Оценка: 1 (1) +2
Здравствуйте, LaptevVV, Вы писали:

LVV>1. Явно падает по неправильному указателю. Скорее всего нулевой.


С чего такой вывод? Ну, и код я привел, можно пальцем ткнуть, где там получается неправильный указатель?


LVV>2. В С++17 есть уже файловая система, и там уже есть что-то вроде exist() для файла.


Угу, только между тем моментом, когда я проверил существование файла, и тем моментом, когда я его создал — кто-то другой может захотеть сделать тоже самое, и никто ему и слова не скажет
Re[3]: std::fopen падает в релизе с ошибкой 0xc0000417
От: Pavel Dvorkin Россия  
Дата: 03.02.22 15:25
Оценка:
Здравствуйте, удусекшл, Вы писали:

У>MSVC с ключиком "ISO C++17 Standard (/std:c++17)"


Сделай на всякий случай простой тест на C с жестко зашитыми char[] массивами.
With best regards
Pavel Dvorkin
Re: std::fopen падает в релизе с ошибкой 0xc0000417
От: ononim  
Дата: 03.02.22 16:30
Оценка: +1
_set_invalid_parameter_handler
Как много веселых ребят, и все делают велосипед...
Re: std::fopen падает в релизе с ошибкой 0xc0000417
От: Alexander G Украина  
Дата: 03.02.22 16:30
Оценка:
Здравствуйте, удусекшл, Вы писали:

У>The thread 0x4730 has exited with code -1073740777 (0xc0000417).

У>// Тут ёще куча потоков с тем же кодом завершается

Это STATUS_INVALID_CRUNTIME_PARAMETER, по идее:
* Должно быть видно под отладчиком как Win32 Exception с таким кодом.
* Должно ловиться через обработчик _set_invalid_parameter_handler.

Если несвязанные потоки завершаются так, это может быть порча памяти, если есть возможность запустить с Address Sanitizer, я бы его попробовал. Если нет — AppVerifier с Heaps с меньшей, но ненулевой вероятностью может что-то поймать.
Русский военный корабль идёт ко дну!
Re[3]: std::fopen падает в релизе с ошибкой 0xc0000417
От: Alexander G Украина  
Дата: 03.02.22 16:36
Оценка:
Здравствуйте, удусекшл, Вы писали:

PD>>File access mode flag "x" can optionally be appended to "w" or "w+" specifiers. This flag forces the function to fail if the file exists, instead of overwriting it. (C++17)


PD>>https://en.cppreference.com/w/cpp/io/c/fopen


У>MSVC с ключиком "ISO C++17 Standard (/std:c++17)"


Для функций C runtime на самом деле имеет значение не ключик, а версия рантайма.
При сборке с /MD берётся системный рантайм, который может быть слишком старый.
VS 2015, 2017, 2019, 2022 используют те же самые DLL, т.е. програма может взять версию от 2015.

свежий vcredist может в этом случае помочь
Русский военный корабль идёт ко дну!
Отредактировано 03.02.2022 16:37 Alexander G . Предыдущая версия .
Re[4]: std::fopen падает в релизе с ошибкой 0xc0000417
От: Pavel Dvorkin Россия  
Дата: 03.02.22 16:41
Оценка:
Здравствуйте, Alexander G, Вы писали:

AG>Для функций C runtime на самом деле имеет значение не ключик, а версия рантайма.

AG>При сборке с /MD берётся системный рантайм, который может быть слишком старый.
AG>VS 2015, 2017, 2019, 2022 используют те же самые DLL, т.е. програма может взять версию от 2015.

Я тоже об этом подумал, но ТС ведь делает в среде VS, а в этом случае должен браться рантайм от нее. А поскольку он явно с рантаймами не колдовал, то должен браться 17.
With best regards
Pavel Dvorkin
Re: std::fopen падает в релизе с ошибкой 0xc0000417
От: B0FEE664  
Дата: 03.02.22 16:46
Оценка:
Здравствуйте, удусекшл, Вы писали:

У>Такой код:

У>
    if (!appConfig.outputFilename.empty())
У>    {
У>        std::string openMode = "w";
У>        if (!appConfig.getOptOverwrite())
У>            openMode.append("x"); // This flag forces the function to fail if the file exists, instead of overwriting it.


У>        cout<<"try to create file '" << appConfig.outputFilename << "', open mode: '" << openMode << "'" << endl;

У>        errno = 0;
У>        std::FILE* pFile = std::fopen( appConfig.outputFilename.c_str(), openMode.c_str() );

У>        //...
У>    }
У>


В этом коде меня смущает только errno:

On some ancient systems, <errno.h> was not present or did not
declare errno, so that it was necessary to declare errno manually
(i.e., extern int errno). Do not do this. It long ago ceased to
be necessary, and it will cause problems with modern versions of
the C library.

Следует проверить её декларацию. Зачем, кстати, её занулять?

У>// Тут ёще куча потоков с тем же кодом завершается

Раз приложение многопоточное, то следует убедиться, что appConfig никто не меняет.
Раз приложение многопоточное, то место падения может не соответствовать причине падения.

У>В Debug сборке всё работает без нареканий. Я видимо, где-то протупил, но не пойму где.

Скорее всего ошибка вне этого куска кода.
И каждый день — без права на ошибку...
Re[5]: std::fopen падает в релизе с ошибкой 0xc0000417
От: Alexander G Украина  
Дата: 03.02.22 16:47
Оценка:
Здравствуйте, Pavel Dvorkin, Вы писали:

PD>Я тоже об этом подумал, но ТС ведь делает в среде VS, а в этом случае должен браться рантайм от нее. А поскольку он явно с рантаймами не колдовал, то должен браться 17.


Не обязательно. Можно установить более старый рантайм после установки VS 2017+ например, удалив рантайм, и установив старый vcredist, какой-либо инсталлер в принципе на такое способен без ведома пользователя. Отладочные DLLки более защищены от такого, т.к. официально не являются redistributable и не входят ни в какой vcredist.
Русский военный корабль идёт ко дну!
Re[3]: std::fopen падает в релизе с ошибкой 0xc0000417
От: LaptevVV Россия  
Дата: 03.02.22 16:51
Оценка:
LVV>>1. Явно падает по неправильному указателю. Скорее всего нулевой.
У>С чего такой вывод? Ну, и код я привел, можно пальцем ткнуть, где там получается неправильный указатель?
Вывод из опыта.
Каким компилятором компилил?

LVV>>2. В С++17 есть уже файловая система, и там уже есть что-то вроде exist() для файла.

У>Угу, только между тем моментом, когда я проверил существование файла, и тем моментом, когда я его создал — кто-то другой может захотеть сделать тоже самое, и никто ему и слова не скажет
Дык в твоем коде это может случится в любом месте между любых двух строк кода.
И с чего там у тебя "wx" ?
https://ru.cppreference.com/w/c/io/fopen
тут икса нет ни разу.
Хочешь быть счастливым — будь им!
Без булдырабыз!!!
Re: std::fopen падает в релизе с ошибкой 0xc0000417
От: ArtDenis Россия  
Дата: 03.02.22 17:53
Оценка:
Здравствуйте, удусекшл, Вы писали:

У>Здравствуйте!


Я конечно может туплю, но если воспроизводится в отладчике, в чём проблема посмотреть где именно вылетает и какая причина вылета потока? Callstack и значения аргументов функций в точке падения должны же быть видны, а отладчик должен встать на место падения, (если не настроен пропуск таких исключений)
[ 🎯 Дартс-лига Уфы | 🌙 Программа для сложения астрофото ]
Re[4]: std::fopen падает в релизе с ошибкой 0xc0000417
От: sergii.p  
Дата: 04.02.22 08:41
Оценка: 1 (1)
Здравствуйте, LaptevVV, Вы писали:

LVV>И с чего там у тебя "wx" ?

LVV>https://ru.cppreference.com/w/c/io/fopen
LVV>тут икса нет ни разу.

это фишка С++17
https://en.cppreference.com/w/cpp/io/c/fopen

File access mode flag "x" can optionally be appended to "w" or "w+" specifiers. This flag forces the function to fail if the file exists, instead of overwriting it. (C++17)

Re[2]: std::fopen падает в релизе с ошибкой 0xc0000417
От: удусекшл  
Дата: 04.02.22 10:07
Оценка:
Здравствуйте, ononim, Вы писали:

O>_set_invalid_parameter_handler


  myInvalidParameterHandler
void myInvalidParameterHandler(const wchar_t* expression,
   const wchar_t* function, 
   const wchar_t* file, 
   unsigned int line, 
   uintptr_t pReserved)
{
   wprintf(L"Invalid parameter detected in function %s."
            L" File: %s Line: %d\n", function, file, line);
   wprintf(L"Expression: %s\n", expression);
   abort();
}


печатает

Invalid parameter detected in function (null). File: (null) Line: 0
Expression: (null)


Что-то не особо понятнее стало
Re[4]: std::fopen падает в релизе с ошибкой 0xc0000417
От: удусекшл  
Дата: 04.02.22 10:14
Оценка:
Здравствуйте, Alexander G, Вы писали:

AG>Для функций C runtime на самом деле имеет значение не ключик, а версия рантайма.

AG>При сборке с /MD берётся системный рантайм, который может быть слишком старый.
AG>VS 2015, 2017, 2019, 2022 используют те же самые DLL, т.е. програма может взять версию от 2015.

AG>свежий vcredist может в этом случае помочь


У меня вот такой
  Скрытый текст


Предлагает "исправить"

ЗЫ Не помогло
Re[2]: std::fopen падает в релизе с ошибкой 0xc0000417
От: удусекшл  
Дата: 04.02.22 10:18
Оценка:
Здравствуйте, B0FEE664, Вы писали:

BFE>Следует проверить её декларацию. Зачем, кстати, её занулять?


На всякий случай
Впрочем, я убрал эту строчку, ничего не изменилось


У>>// Тут ёще куча потоков с тем же кодом завершается

BFE>Раз приложение многопоточное, то следует убедиться, что appConfig никто не меняет.
BFE>Раз приложение многопоточное, то место падения может не соответствовать причине падения.

Приложение однопоточное, мелкая тулза, весь main на 100 строчек. Я хз, почему в MSVCшный output выводится инфа о куче потоков. Думаю, это а) рантайм чего-то делате хз зачем, б) отладчик студийный тоже чего-то запускает


У>>В Debug сборке всё работает без нареканий. Я видимо, где-то протупил, но не пойму где.

BFE>Скорее всего ошибка вне этого куска кода.

Вероятно. Но мне как-то легче не стало
Re[5]: std::fopen падает в релизе с ошибкой 0xc0000417
От: Alexander G Украина  
Дата: 04.02.22 10:26
Оценка:
Здравствуйте, удусекшл, Вы писали:

У>У меня вот такой


Значит, проблема не в этом. 14.29 это последняя версия 2019
Русский военный корабль идёт ко дну!
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.