Skip to content

Commit

Permalink
windows: Before SDL_main has run, use WideCharToMultibyte, not SDL_ic…
Browse files Browse the repository at this point in the history
…onv.

Otherwise, this will crash if the app sets its own SDL_malloc allocator, since
SDL_iconv uses SDL_malloc.

WideCharToMultibyte lets us calculate the needed memory for the argv[] string
conversions, and then we use the win32 HeapAlloc() API to get some memory
for it.

Fixes #8967.
  • Loading branch information
icculus committed May 23, 2024
1 parent 86b2f44 commit 25024ea
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 16 deletions.
19 changes: 11 additions & 8 deletions src/core/gdk/SDL_gdk.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -108,18 +108,21 @@ int SDL_RunApp(int, char**, SDL_main_func mainFunction, void *reserved)
return OutOfMemory();
}
for (i = 0; i < argc; ++i) {
DWORD len;
char *arg = WIN_StringToUTF8W(argvw[i]);
if (arg == NULL) {
return OutOfMemory();
const int utf8size = WideCharToMultiByte(CP_UTF8, 0, argvw[i], -1, NULL, 0, NULL, NULL);
if (!utf8size) { // uhoh?
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Fatal Error", "Error processing command line arguments", NULL);
return -1;
}
len = (DWORD)SDL_strlen(arg);
argv[i] = (char *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len + 1);

argv[i] = (char *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, utf8size); // this size includes the null-terminator character.
if (!argv[i]) {
return OutOfMemory();
}
SDL_memcpy(argv[i], arg, len);
SDL_free(arg);

if (WideCharToMultiByte(CP_UTF8, 0, argvw[i], -1, argv[i], utf8size, NULL, NULL) == 0) { // failed? uhoh!
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Fatal Error", "Error processing command line arguments", NULL);
return -1;
}
}
argv[i] = NULL;
LocalFree(argvw);
Expand Down
19 changes: 11 additions & 8 deletions src/core/windows/SDL_windows.c
Original file line number Diff line number Diff line change
Expand Up @@ -431,18 +431,21 @@ int MINGW32_FORCEALIGN SDL_RunApp(int _argc, char* _argv[], SDL_main_func mainFu
return OutOfMemory();
}
for (i = 0; i < argc; ++i) {
DWORD len;
char *arg = WIN_StringToUTF8W(argvw[i]);
if (!arg) {
return OutOfMemory();
const int utf8size = WideCharToMultiByte(CP_UTF8, 0, argvw[i], -1, NULL, 0, NULL, NULL);
if (!utf8size) { // uhoh?
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Fatal Error", "Error processing command line arguments", NULL);
return -1;
}
len = (DWORD)SDL_strlen(arg);
argv[i] = (char *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len + 1);

argv[i] = (char *)HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, utf8size); // this size includes the null-terminator character.
if (!argv[i]) {
return OutOfMemory();
}
SDL_memcpy(argv[i], arg, len);
SDL_free(arg);

if (WideCharToMultiByte(CP_UTF8, 0, argvw[i], -1, argv[i], utf8size, NULL, NULL) == 0) { // failed? uhoh!
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "Fatal Error", "Error processing command line arguments", NULL);
return -1;
}
}
argv[i] = NULL;
LocalFree(argvw);
Expand Down

0 comments on commit 25024ea

Please sign in to comment.