diff --git a/daemon/gamemode-env.c b/daemon/gamemode-env.c new file mode 100644 index 0000000..655df33 --- /dev/null +++ b/daemon/gamemode-env.c @@ -0,0 +1,96 @@ +/* + +Copyright (c) 2017-2018, Feral Interactive +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + + * Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + * Neither the name of Feral Interactive nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +POSSIBILITY OF SUCH DAMAGE. + + */ + +#define _GNU_SOURCE + +#include "gamemode.h" + +#include +#include +#include +#include +#include +#include + +/** + * Lookup the process environment for a specific variable or return NULL. + * Requires an open directory FD from /proc/PID. + */ +char *game_mode_lookup_proc_env(const procfd_t proc_fd, const char *var) +{ + char *environ = NULL; + + int fd = openat(proc_fd, "environ", O_RDONLY | O_CLOEXEC); + if (fd != -1) { + FILE *stream = fdopen(fd, "r"); + if (stream) { + /* Read every \0 terminated line from the environment */ + char *line = NULL; + size_t len = 0; + size_t pos = strlen(var) + 1; + while (!environ && (getdelim(&line, &len, 0, stream) != -1)) { + /* Find a match including the "=" suffix */ + if ((len > pos) && (strncmp(line, var, strlen(var)) == 0) && (line[pos - 1] == '=')) + environ = strndup(line + pos, len - pos); + } + free(line); + fclose(stream); + } else + close(fd); + } + + /* If found variable is empty, skip it */ + if (environ && !strlen(environ)) { + free(environ); + environ = NULL; + } + + return environ; +} + +/** + * Lookup the home directory of the user in a safe way. + */ +char *game_mode_lookup_user_home(void) +{ + /* Try loading env HOME first */ + const char *home = secure_getenv("HOME"); + if (!home) { + /* If HOME is not defined (or out of context), fall back to passwd */ + struct passwd *pw = getpwuid(getuid()); + if (!pw) + return NULL; + home = pw->pw_dir; + } + + /* Try to allocate into our heap */ + return home ? strdup(home) : NULL; +} diff --git a/daemon/gamemode.c b/daemon/gamemode.c index e2578a2..1f550d2 100644 --- a/daemon/gamemode.c +++ b/daemon/gamemode.c @@ -43,7 +43,6 @@ POSSIBILITY OF SUCH DAMAGE. #include #include #include -#include #include #include #include @@ -719,61 +718,6 @@ GameModeContext *game_mode_context_instance() return &instance; } -/** - * Lookup the process environment for a specific variable or return NULL. - * Requires an open directory FD from /proc/PID. - */ -static char *game_mode_lookup_proc_env(const procfd_t proc_fd, const char *var) -{ - char *environ = NULL; - - int fd = openat(proc_fd, "environ", O_RDONLY | O_CLOEXEC); - if (fd != -1) { - FILE *stream = fdopen(fd, "r"); - if (stream) { - /* Read every \0 terminated line from the environment */ - char *line = NULL; - size_t len = 0; - size_t pos = strlen(var) + 1; - while (!environ && (getdelim(&line, &len, 0, stream) != -1)) { - /* Find a match including the "=" suffix */ - if ((len > pos) && (strncmp(line, var, strlen(var)) == 0) && (line[pos - 1] == '=')) - environ = strndup(line + pos, len - pos); - } - free(line); - fclose(stream); - } else - close(fd); - } - - /* If found variable is empty, skip it */ - if (environ && !strlen(environ)) { - free(environ); - environ = NULL; - } - - return environ; -} - -/** - * Lookup the home directory of the user in a safe way. - */ -static char *game_mode_lookup_user_home(void) -{ - /* Try loading env HOME first */ - const char *home = secure_getenv("HOME"); - if (!home) { - /* If HOME is not defined (or out of context), fall back to passwd */ - struct passwd *pw = getpwuid(getuid()); - if (!pw) - return NULL; - home = pw->pw_dir; - } - - /* Try to allocate into our heap */ - return home ? strdup(home) : NULL; -} - /** * Attempt to resolve the exe for wine-preloader. * This function is used if game_mode_context_find_exe() identified the diff --git a/daemon/gamemode.h b/daemon/gamemode.h index 81f68b7..f9df524 100644 --- a/daemon/gamemode.h +++ b/daemon/gamemode.h @@ -88,6 +88,13 @@ bool game_mode_context_unregister(GameModeContext *self, pid_t pid); */ int game_mode_context_query_status(GameModeContext *self, pid_t pid); +/** gamemode-env.c + * Provides internal API functions specific to working environment + * variables. + */ +char *game_mode_lookup_proc_env(const procfd_t proc_fd, const char *var); +char *game_mode_lookup_user_home(void); + /** gamemode-proc.c * Provides internal API functions specific to working with process * environments. diff --git a/daemon/meson.build b/daemon/meson.build index 34d8caf..5f4dcc2 100644 --- a/daemon/meson.build +++ b/daemon/meson.build @@ -18,6 +18,7 @@ link_daemon_common = declare_dependency( daemon_sources = [ 'main.c', 'gamemode.c', + 'gamemode-env.c', 'gamemode-proc.c', 'daemonize.c', 'dbus_messaging.c',