mirror of
https://github.com/ClassiCube/ClassiCube.git
synced 2025-09-16 11:06:06 -04:00
Merge pull request #934 from UnknownShadow200/GameArgsFix
Support spaces in command line arguments when starting game from launcher
This commit is contained in:
commit
4f79864d5e
@ -86,7 +86,7 @@ static CC_NOINLINE void InitFramebuffer(void) {
|
||||
*#########################################################################################################################*/
|
||||
static cc_uint64 lastJoin;
|
||||
cc_bool Launcher_StartGame(const cc_string* user, const cc_string* mppass, const cc_string* ip, const cc_string* port, const cc_string* server) {
|
||||
cc_string args; char argsBuffer[512];
|
||||
cc_string args[4]; int numArgs;
|
||||
TimeMS now;
|
||||
cc_result res;
|
||||
|
||||
@ -106,11 +106,16 @@ cc_bool Launcher_StartGame(const cc_string* user, const cc_string* mppass, const
|
||||
/* Otherwise can get 'file already in use' errors on startup */
|
||||
Options_SaveIfChanged();
|
||||
|
||||
String_InitArray(args, argsBuffer);
|
||||
String_AppendString(&args, user);
|
||||
if (mppass->length) String_Format3(&args, " %s %s %s", mppass, ip, port);
|
||||
args[0] = *user;
|
||||
numArgs = 1;
|
||||
if (mppass->length) {
|
||||
args[1] = *mppass;
|
||||
args[2] = *ip;
|
||||
args[3] = *port;
|
||||
numArgs = 4;
|
||||
}
|
||||
|
||||
res = Process_StartGame(&args);
|
||||
res = Process_StartGame2(args, numArgs);
|
||||
if (res) { Logger_SysWarn(res, "starting game"); return false; }
|
||||
|
||||
#ifdef CC_BUILD_MOBILE
|
||||
|
@ -63,7 +63,7 @@ describe exists (e.g. Http_DescribeError), that should be preferred. */
|
||||
cc_bool Platform_DescribeError(cc_result res, cc_string* dst);
|
||||
|
||||
/* Starts the game with the given arguments. */
|
||||
CC_API cc_result Process_StartGame(const cc_string* args);
|
||||
CC_API cc_result Process_StartGame2(const cc_string* args, int numArgs);
|
||||
/* Terminates the process with the given return code. */
|
||||
CC_API void Process_Exit(cc_result code);
|
||||
/* Starts the platform-specific program to open the given url or filename. */
|
||||
|
@ -27,11 +27,15 @@ void Platform_Log(const char* msg, int len) {
|
||||
/*########################################################################################################################*
|
||||
*-----------------------------------------------------Process/Module------------------------------------------------------*
|
||||
*#########################################################################################################################*/
|
||||
static char gameArgsBuffer[512];
|
||||
static cc_string gameArgs = String_FromArray(gameArgsBuffer);
|
||||
static char gameArgs[GAME_MAX_CMDARGS][STRING_SIZE];
|
||||
static int gameNumArgs;
|
||||
|
||||
cc_result Process_StartGame(const cc_string* args) {
|
||||
String_Copy(&gameArgs, args);
|
||||
cc_result Process_StartGame2(const cc_string* args, int numArgs) {
|
||||
for (int i = 0; i < numArgs; i++) {
|
||||
String_CopyToRawArray(gameArgs[i], &args[i]);
|
||||
}
|
||||
|
||||
gameNumArgs = numArgs;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -94,13 +98,14 @@ void Platform_ShareScreenshot(const cc_string* filename) {
|
||||
*-----------------------------------------------------Configuration-------------------------------------------------------*
|
||||
*#########################################################################################################################*/
|
||||
int Platform_GetCommandLineArgs(int argc, STRING_REF char** argv, cc_string* args) {
|
||||
int count = 0;
|
||||
if (gameArgs.length) {
|
||||
count = String_UNSAFE_Split(&gameArgs, ' ', args, GAME_MAX_CMDARGS);
|
||||
/* clear arguments so after game is closed, launcher is started */
|
||||
gameArgs.length = 0;
|
||||
int count = gameNumArgs;
|
||||
for (int i = 0; i < count; i++) {
|
||||
args[i] = String_FromRawArray(gameArgs[i]);
|
||||
}
|
||||
return count;
|
||||
|
||||
// clear arguments so after game is closed, launcher is started
|
||||
gameNumArgs = 0;
|
||||
return count;
|
||||
}
|
||||
|
||||
cc_result Platform_SetDefaultCurrentDirectory(int argc, char **argv) {
|
||||
|
@ -622,25 +622,20 @@ static cc_result Process_RawStart(const char* path, char** argv) {
|
||||
|
||||
static cc_result Process_RawGetExePath(char* path, int* len);
|
||||
|
||||
cc_result Process_StartGame(const cc_string* args) {
|
||||
char path[NATIVE_STR_LEN], raw[NATIVE_STR_LEN];
|
||||
cc_result Process_StartGame2(const cc_string* args, int numArgs) {
|
||||
char raw[GAME_MAX_CMDARGS][NATIVE_STR_LEN];
|
||||
char path[NATIVE_STR_LEN];
|
||||
int i, j, len = 0;
|
||||
char* argv[15];
|
||||
|
||||
cc_result res = Process_RawGetExePath(path, &len);
|
||||
if (res) return res;
|
||||
path[len] = '\0';
|
||||
argv[0] = path;
|
||||
|
||||
Platform_EncodeUtf8(raw, args);
|
||||
argv[0] = path; argv[1] = raw;
|
||||
|
||||
/* need to null-terminate multiple arguments */
|
||||
for (i = 0, j = 2; raw[i] && i < Array_Elems(raw); i++) {
|
||||
if (raw[i] != ' ') continue;
|
||||
|
||||
/* null terminate previous argument */
|
||||
raw[i] = '\0';
|
||||
argv[j++] = &raw[i + 1];
|
||||
for (i = 0, j = 1; i < numArgs; i++, j++) {
|
||||
Platform_EncodeUtf8(raw[i], &args[i]);
|
||||
argv[j] = raw[i];
|
||||
}
|
||||
|
||||
if (defaultDirectory) { argv[j++] = defaultDirectory; }
|
||||
|
@ -357,7 +357,9 @@ cc_result Socket_Poll(cc_socket s, int mode, cc_bool* success) {
|
||||
/*########################################################################################################################*
|
||||
*-----------------------------------------------------Process/Module------------------------------------------------------*
|
||||
*#########################################################################################################################*/
|
||||
cc_result Process_StartGame(const cc_string* args) { return ERR_NOT_SUPPORTED; }
|
||||
cc_result Process_StartGame(const cc_string* args, int numArgs) {
|
||||
return ERR_NOT_SUPPORTED;
|
||||
}
|
||||
void Process_Exit(cc_result code) {
|
||||
/* Window isn't implicitly closed when process is exited */
|
||||
if (code) Window_Close();
|
||||
|
@ -547,13 +547,13 @@ static cc_result Process_RawGetExePath(WCHAR* path, int* len) {
|
||||
return *len ? 0 : GetLastError();
|
||||
}
|
||||
|
||||
cc_result Process_StartGame(const cc_string* args) {
|
||||
cc_result Process_StartGame2(const cc_string* args, int numArgs) {
|
||||
WCHAR path[NATIVE_STR_LEN + 1], raw[NATIVE_STR_LEN];
|
||||
cc_string argv; char argvBuffer[NATIVE_STR_LEN];
|
||||
STARTUPINFOW si = { 0 };
|
||||
PROCESS_INFORMATION pi = { 0 };
|
||||
cc_result res;
|
||||
int len;
|
||||
int len, i;
|
||||
|
||||
Process_RawGetExePath(path, &len);
|
||||
path[len] = '\0';
|
||||
@ -561,8 +561,15 @@ cc_result Process_StartGame(const cc_string* args) {
|
||||
|
||||
String_InitArray(argv, argvBuffer);
|
||||
/* Game doesn't actually care about argv[0] */
|
||||
String_Format1(&argv, "cc %s", args);
|
||||
String_UNSAFE_TrimEnd(&argv);
|
||||
String_AppendConst(&argv, "cc");
|
||||
for (i = 0; i < numArgs; i++)
|
||||
{
|
||||
if (String_IndexOf(&args[i], ' ') >= 0) {
|
||||
String_Format1(&argv, " \"%s\"", &args[i]);
|
||||
} else {
|
||||
String_Format1(&argv, " %s", &args[i]);
|
||||
}
|
||||
}
|
||||
Platform_EncodeUtf16(raw, &argv);
|
||||
|
||||
if (CreateProcessW(path, raw, NULL, NULL,
|
||||
@ -636,7 +643,7 @@ cc_result Updater_Start(const char** action) {
|
||||
if (!MoveFileExW(UPDATE_SRC, path, MOVEFILE_REPLACE_EXISTING)) return GetLastError();
|
||||
|
||||
*action = "Restarting game";
|
||||
return Process_StartGame(&String_Empty);
|
||||
return Process_StartGame2(NULL, 0);
|
||||
}
|
||||
|
||||
cc_result Updater_GetBuildTime(cc_uint64* timestamp) {
|
||||
|
@ -85,7 +85,7 @@ static void LimitFPS(void) {
|
||||
float cooldown = gfx_targetTime - gfx_actualTime;
|
||||
Thread_Sleep((int)(cooldown + 0.5f));
|
||||
|
||||
/* also accumulate Thread_Sleep duration, as actual sleep
|
||||
/* also accumulate Thread_Sleep duration, as actual sleep */
|
||||
/* duration can significantly deviate from requested time */
|
||||
/* (e.g. requested 4ms, but actually slept for 8ms) */
|
||||
cc_uint64 sleepEnd = Stopwatch_Measure();
|
||||
|
@ -406,6 +406,9 @@ cc_result Updater_SetNewBuildTime(cc_uint64 t) { return ERR_NOT_SUPPORTED; }
|
||||
/*########################################################################################################################*
|
||||
*--------------------------------------------------------Platform--------------------------------------------------------*
|
||||
*#########################################################################################################################*/
|
||||
static char gameArgs[GAME_MAX_CMDARGS][STRING_SIZE];
|
||||
static int gameNumArgs;
|
||||
|
||||
cc_result Process_StartOpen(const cc_string* args) {
|
||||
char raw[NATIVE_STR_LEN];
|
||||
NSURL* url;
|
||||
@ -418,19 +421,23 @@ cc_result Process_StartOpen(const cc_string* args) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static char gameArgsBuffer[512];
|
||||
static cc_string gameArgs = String_FromArray(gameArgsBuffer);
|
||||
cc_result Process_StartGame(const cc_string* args) {
|
||||
String_Copy(&gameArgs, args);
|
||||
cc_result Process_StartGame2(const cc_string* args, int numArgs) {
|
||||
for (int i = 0; i < numArgs; i++) {
|
||||
String_CopyToRawArray(gameArgs[i], &args[i]);
|
||||
}
|
||||
|
||||
gameNumArgs = numArgs;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int Platform_GetCommandLineArgs(int argc, STRING_REF char** argv, cc_string* args) {
|
||||
if (!gameArgs.length) return 0;
|
||||
|
||||
int count = String_UNSAFE_Split(&gameArgs, ' ', args, GAME_MAX_CMDARGS);
|
||||
// clear arguments so after game is closed, launcher is started again
|
||||
gameArgs.length = 0;
|
||||
int count = gameNumArgs;
|
||||
for (int i = 0; i < count; i++) {
|
||||
args[i] = String_FromRawArray(gameArgs[i]);
|
||||
}
|
||||
|
||||
// clear arguments so after game is closed, launcher is started
|
||||
gameNumArgs = 0;
|
||||
return count;
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user