diff --git a/steam-runtime-tools/utils.c b/steam-runtime-tools/utils.c index 656d36e14a4da8ec037c88d906cc676677c83acb..a52f07947597aeb20efa87b3dc3fa024715be6a9 100644 --- a/steam-runtime-tools/utils.c +++ b/steam-runtime-tools/utils.c @@ -154,6 +154,8 @@ _srt_check_not_setuid (void) "/lib/" _SRT_MULTIARCH #define RELOCATABLE_PKGLIBDIR \ MULTIARCH_LIBDIR "/steam-runtime-tools-" _SRT_API_MAJOR +#define PKGLIBEXECDIR \ + "/libexec/steam-runtime-tools-" _SRT_API_MAJOR /** * _srt_process_timeout_wait_status: @@ -234,17 +236,41 @@ _srt_find_myself (const char **helpers_path_out, goto out; } - g_debug ("Found _srt_find_myself() in %s", map->l_name); - dir = g_path_get_dirname (map->l_name); + if (map->l_name == NULL || map->l_name[0] == '\0') + { + char *exe = realpath ("/proc/self/exe", NULL); + + if (exe == NULL) + { + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, + "Unable to locate main executable"); + goto out; + } + + g_debug ("Found _srt_find_myself() in main executable %s", exe); + dir = g_path_get_dirname (exe); + free (exe); + } + else + { + g_debug ("Found _srt_find_myself() in %s", map->l_name); + dir = g_path_get_dirname (map->l_name); + } if (g_str_has_suffix (dir, RELOCATABLE_PKGLIBDIR)) dir[strlen (dir) - strlen (RELOCATABLE_PKGLIBDIR)] = '\0'; else if (g_str_has_suffix (dir, MULTIARCH_LIBDIR)) dir[strlen (dir) - strlen (MULTIARCH_LIBDIR)] = '\0'; + else if (g_str_has_suffix (dir, PKGLIBEXECDIR)) + dir[strlen (dir) - strlen (PKGLIBEXECDIR)] = '\0'; + else if (g_str_has_suffix (dir, "/libexec")) + dir[strlen (dir) - strlen ("/libexec")] = '\0'; else if (g_str_has_suffix (dir, "/lib64")) dir[strlen (dir) - strlen ("/lib64")] = '\0'; else if (g_str_has_suffix (dir, "/lib")) dir[strlen (dir) - strlen ("/lib")] = '\0'; + else if (g_str_has_suffix (dir, "/bin")) + dir[strlen (dir) - strlen ("/bin")] = '\0'; /* If the library was found in /lib/MULTIARCH, /lib64 or /lib on a * merged-/usr system, assume --prefix=/usr (/libexec doesn't diff --git a/tests/find-myself.c b/tests/find-myself.c new file mode 100644 index 0000000000000000000000000000000000000000..bcab0fda281b6e97ab96fb0658594167617c6e9d --- /dev/null +++ b/tests/find-myself.c @@ -0,0 +1,59 @@ +/* + * Copyright © 2020 Collabora Ltd. + * + * SPDX-License-Identifier: MIT + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY + * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, + * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE + * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +#include <steam-runtime-tools/steam-runtime-tools.h> + +#include <glib.h> + +#include "steam-runtime-tools/glib-backports-internal.h" +#include "steam-runtime-tools/utils-internal.h" + +/* + * Usage: copy the compiled executable into some random prefix and + * run it. + * + * If you put it in /prefix/bin, /prefix/libexec or + * /prefix/libexec/steam-runtime-tools-0, it should say that its prefix + * is /prefix. + */ + +int +main (int argc, + char **argv) +{ + g_autoptr(GError) error = NULL; + const char *helpers = NULL; + const char *prefix = _srt_find_myself (&helpers, &error); + + if (prefix == NULL) + { + g_warning ("Unable to find myself: %s", error->message); + return 1; + } + + g_print ("Prefix: %s\n", prefix); + g_print ("Looking for helpers in: %s\n", helpers); + return 0; +} diff --git a/tests/meson.build b/tests/meson.build index 3bf5760d11b455b73ff8eecb6ff1c0208fba7226..bc04ff99677b9b92aecec8ffc2be4b3ac5bf2e09 100644 --- a/tests/meson.build +++ b/tests/meson.build @@ -187,6 +187,31 @@ foreach test_info : tests endif endforeach +# Helpers and manual tests statically linked to libsteam-r-t +foreach helper : [ + 'find-myself', +] + executable( + helper, + files(helper + '.c'), + c_args : [ + '-D_SRT_MULTIARCH="' + multiarch + '"', + ], + dependencies : [ + glib, + gobject, + gio_unix, + json_glib, + libglnx_dep, + libsteamrt_static_dep, + test_utils_static_libsteamrt_dep, + ], + include_directories : project_include_dirs, + install : get_option('installed_tests'), + install_dir : tests_dir, + ) +endforeach + # A mock implementation of check-locale that offers lots of locales executable( 'mock-check-locale',