From: Michael Tremer Date: Sat, 19 Oct 2024 12:47:13 +0000 (+0000) Subject: jail: Create helper function to capture output X-Git-Tag: 0.9.30~989 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=083d04415d1ee1122611db928a305a3269e0b06f;p=pakfire.git jail: Create helper function to capture output That way, we can have the length as an extra argument. Signed-off-by: Michael Tremer --- diff --git a/src/libpakfire/build.c b/src/libpakfire/build.c index 4704239cf..f24d9eaad 100644 --- a/src/libpakfire/build.c +++ b/src/libpakfire/build.c @@ -2466,7 +2466,7 @@ PAKFIRE_EXPORT int pakfire_build_shell(struct pakfire_build* build, const char* // Run the command (if given) if (argv) - return pakfire_jail_exec(build->jail, argv, 0, NULL); + return pakfire_jail_exec(build->jail, argv, 0); // Otherwise run the shell return pakfire_jail_shell(build->jail); diff --git a/src/libpakfire/include/pakfire/jail.h b/src/libpakfire/include/pakfire/jail.h index 72338a641..4b82b08bd 100644 --- a/src/libpakfire/include/pakfire/jail.h +++ b/src/libpakfire/include/pakfire/jail.h @@ -68,7 +68,10 @@ enum pakfire_jail_exec_flags { PAKFIRE_JAIL_HAS_LOOP_DEVICES = (1 << 3), }; -int pakfire_jail_exec(struct pakfire_jail* jail, const char* argv[], int flags, char** output); +int pakfire_jail_exec(struct pakfire_jail* jail, const char* argv[], int flags); + +int pakfire_jail_exec_capture_output(struct pakfire_jail* jail, + const char* argv[], int flags, char** output, size_t* length); // Resource limits int pakfire_jail_set_cgroup(struct pakfire_jail* jail, struct pakfire_cgroup* cgroup); @@ -79,7 +82,8 @@ int pakfire_jail_communicate( pakfire_pty_stdout_callback stdout_callback, void* stdout_data); // Convenience functions -int pakfire_jail_run(struct pakfire* pakfire, const char* argv[], int flags, char** output); +int pakfire_jail_run(struct pakfire* pakfire, + const char* argv[], int flags, char** output, size_t* output_length); int pakfire_jail_run_script(struct pakfire* pakfire, const char* script, const size_t length, const char* argv[], int flags); diff --git a/src/libpakfire/jail.c b/src/libpakfire/jail.c index cb144a02f..bfca392a6 100644 --- a/src/libpakfire/jail.c +++ b/src/libpakfire/jail.c @@ -1341,7 +1341,7 @@ static int __pakfire_jail_exec(struct pakfire_jail* jail, const char* argv[], int flags, pakfire_pty_stdin_callback stdin_callback, void* stdin_data, pakfire_pty_stdout_callback stdout_callback, void* stdout_data, - char** output) { + char** output, size_t* output_length) { int pty_flags = 0; int r; @@ -1522,9 +1522,8 @@ static int __pakfire_jail_exec(struct pakfire_jail* jail, } // Return the output - if (output) { - *output = pakfire_pty_output(ctx.pty, NULL); - } + if (output) + *output = pakfire_pty_output(ctx.pty, output_length); ERROR: // Destroy the temporary cgroup (if any) @@ -1560,9 +1559,13 @@ ERROR: return ctx.exit; } -int pakfire_jail_exec(struct pakfire_jail* jail, - const char* argv[], int flags, char** output) { - return __pakfire_jail_exec(jail, argv, flags, NULL, NULL, NULL, NULL, output); +int pakfire_jail_exec(struct pakfire_jail* jail, const char* argv[], int flags) { + return __pakfire_jail_exec(jail, argv, flags, NULL, NULL, NULL, NULL, NULL, NULL); +} + +int pakfire_jail_exec_capture_output(struct pakfire_jail* jail, + const char* argv[], int flags, char** output, size_t* length) { + return __pakfire_jail_exec(jail, argv, flags, NULL, NULL, NULL, NULL, output, length); } int pakfire_jail_communicate( @@ -1570,7 +1573,7 @@ int pakfire_jail_communicate( pakfire_pty_stdin_callback stdin_callback, void* stdin_data, pakfire_pty_stdout_callback stdout_callback, void* stdout_data) { return __pakfire_jail_exec(jail, argv, flags, - stdin_callback, stdin_data, stdout_callback, stdout_data, NULL); + stdin_callback, stdin_data, stdout_callback, stdout_data, NULL, NULL); } int pakfire_jail_exec_script(struct pakfire_jail* jail, @@ -1655,7 +1658,8 @@ ERROR: A convenience function that creates a new jail, runs the given command and destroys the jail again. */ -int pakfire_jail_run(struct pakfire* pakfire, const char* argv[], int flags, char** output) { +int pakfire_jail_run(struct pakfire* pakfire, + const char* argv[], int flags, char** output, size_t* output_length) { struct pakfire_jail* jail = NULL; int r; @@ -1665,7 +1669,7 @@ int pakfire_jail_run(struct pakfire* pakfire, const char* argv[], int flags, cha goto ERROR; // Execute the command - r = pakfire_jail_exec(jail, argv, flags, output); + r = pakfire_jail_exec_capture_output(jail, argv, flags, output, output_length); ERROR: if (jail) @@ -1718,7 +1722,7 @@ int pakfire_jail_shell(struct pakfire_jail* jail) { } // Execute /bin/bash - r = pakfire_jail_exec(jail, argv, PAKFIRE_JAIL_INTERACTIVE, NULL); + r = pakfire_jail_exec(jail, argv, PAKFIRE_JAIL_INTERACTIVE); // Raise any errors if (r < 0) @@ -1746,7 +1750,7 @@ static int pakfire_jail_run_if_possible(struct pakfire* pakfire, const char** ar goto ERROR; } - r = pakfire_jail_run(pakfire, argv, 0, NULL); + r = pakfire_jail_run(pakfire, argv, 0, NULL, NULL); ERROR: if (ctx) diff --git a/src/libpakfire/parser.c b/src/libpakfire/parser.c index b7a4a0cb4..dbe7702f9 100644 --- a/src/libpakfire/parser.c +++ b/src/libpakfire/parser.c @@ -476,9 +476,10 @@ static int pakfire_parser_expand_commands(struct pakfire_parser* parser, char** // The output of the command char* output = NULL; + size_t length = 0; // Execute the command inside the Pakfire environment - r = pakfire_jail_run(parser->pakfire, argv, 0, &output); + r = pakfire_jail_run(parser->pakfire, argv, 0, &output, &length); if (r) { // Just log this and continue DEBUG(parser->pakfire, "Command '%s' failed with return code %d\n", command, r); diff --git a/tests/libpakfire/cgroup.c b/tests/libpakfire/cgroup.c index dd00a460b..9cc411334 100644 --- a/tests/libpakfire/cgroup.c +++ b/tests/libpakfire/cgroup.c @@ -74,7 +74,7 @@ static int test_stats(const struct test* t) { // Run a few things for (unsigned int i = 0; i < 3; i++) { - ASSERT_SUCCESS(pakfire_jail_exec(jail, argv, 0, NULL)); + ASSERT_SUCCESS(pakfire_jail_exec(jail, argv, 0)); } // Try reading the stats into some invalid space diff --git a/tests/libpakfire/jail.c b/tests/libpakfire/jail.c index e5b71fc0c..594124e2f 100644 --- a/tests/libpakfire/jail.c +++ b/tests/libpakfire/jail.c @@ -68,7 +68,7 @@ static int test_exit_code(const struct test* t) { ASSERT_SUCCESS(pakfire_jail_create(&jail, t->pakfire)); // Check if we receive the correct exit code - ASSERT(pakfire_jail_exec(jail, argv, 0, NULL) == 123); + ASSERT(pakfire_jail_exec(jail, argv, 0) == 123); // Success r = EXIT_SUCCESS; @@ -92,7 +92,7 @@ static int test_segv(const struct test* t) { ASSERT_SUCCESS(pakfire_jail_create(&jail, t->pakfire)); // Check if we receive the correct exit code - ASSERT(pakfire_jail_exec(jail, argv, 0, NULL) == 139); + ASSERT(pakfire_jail_exec(jail, argv, 0) == 139); // Success r = EXIT_SUCCESS; @@ -135,15 +135,17 @@ FAIL: static int test_exec(const struct test* t) { struct pakfire_jail* jail = NULL; char* output = NULL; + size_t length = 0; // Create a new jail ASSERT_SUCCESS(pakfire_jail_create(&jail, t->pakfire)); // Try to execute something - ASSERT_SUCCESS(pakfire_jail_exec(jail, cmd_hello_world, 0, &output)); + ASSERT_SUCCESS(pakfire_jail_exec_capture_output(jail, cmd_hello_world, 0, &output, &length)); // We should have some output ASSERT_STRING_EQUALS(output, "Hello World!\n"); + ASSERT_EQUALS(length, strlen("Hello World!\n")); // Destroy it ASSERT_NULL(pakfire_jail_unref(jail)); @@ -169,7 +171,7 @@ static int test_launch_into_cgroup(const struct test* t) { ASSERT_SUCCESS(pakfire_jail_set_cgroup(jail, cgroup)); // Run command - ASSERT(pakfire_jail_exec(jail, cmd_hello_world, 0, NULL) == 0); + ASSERT(pakfire_jail_exec(jail, cmd_hello_world, 0) == 0); r = EXIT_SUCCESS; @@ -204,7 +206,7 @@ static int test_nice(const struct test* t) { ASSERT_SUCCESS(pakfire_jail_nice(jail, 5)); // Check if the nice level has been set - ASSERT_SUCCESS(pakfire_jail_exec(jail, argv, 0, &output)); + ASSERT_SUCCESS(pakfire_jail_exec_capture_output(jail, argv, 0, &output, NULL)); ASSERT_STRING_EQUALS(output, "5\n"); // Success @@ -238,10 +240,10 @@ static int test_memory_limit(const struct test* t) { ASSERT_SUCCESS(pakfire_cgroup_set_memory_limit(cgroup, 100 * 1024 * 1024)); // Try to exhaust all memory - ASSERT_FAILURE(pakfire_jail_exec(jail, cmd_exhaust_memory, 0, NULL)); + ASSERT_FAILURE(pakfire_jail_exec(jail, cmd_exhaust_memory, 0)); // A fork bomb should also exhaust all memory - ASSERT_FAILURE(pakfire_jail_exec(jail, cmd_fork_bomb, 0, NULL)); + ASSERT_FAILURE(pakfire_jail_exec(jail, cmd_fork_bomb, 0)); // Success r = EXIT_SUCCESS; @@ -275,7 +277,7 @@ static int test_pid_limit(const struct test* t) { ASSERT_SUCCESS(pakfire_cgroup_set_pid_limit(cgroup, 100)); // Try to fork as many processes as possible - ASSERT_FAILURE(pakfire_jail_exec(jail, cmd_fork_bomb, 0, NULL)); + ASSERT_FAILURE(pakfire_jail_exec(jail, cmd_fork_bomb, 0)); // Success r = EXIT_SUCCESS; @@ -296,7 +298,7 @@ static int test_file_ownership(const struct test* t) { char* output = NULL; // Execute a simple command - ASSERT_SUCCESS(pakfire_jail_run(t->pakfire, cmd_stat_ownership, 0, &output)); + ASSERT_SUCCESS(pakfire_jail_run(t->pakfire, cmd_stat_ownership, 0, &output, NULL)); // Check if the file has been mapped to root/root ASSERT_STRING_EQUALS(output, "uid=0 gid=0\n"); @@ -334,7 +336,7 @@ static int test_bind(const struct test* t) { ASSERT_SUCCESS(pakfire_jail_bind(jail, source, target, MS_RDONLY)); // Check if the mount actually works - ASSERT_SUCCESS(pakfire_jail_exec(jail, argv, 0, NULL)); + ASSERT_SUCCESS(pakfire_jail_exec(jail, argv, 0)); // Success r = EXIT_SUCCESS; @@ -403,7 +405,7 @@ static int test_send_one_signal(const struct test* t, }; // Perform the command - return pakfire_jail_exec(jail, argv, 0, NULL); + return pakfire_jail_exec(jail, argv, 0); } static int test_send_signal(const struct test* t) { @@ -447,7 +449,7 @@ static int test_timeout(const struct test* t) { ASSERT_SUCCESS(pakfire_jail_set_timeout(jail, 1)); // Check if we receive the correct exit code - ASSERT(pakfire_jail_exec(jail, argv, 0, NULL) == 139); + ASSERT(pakfire_jail_exec(jail, argv, 0) == 139); // Success r = EXIT_SUCCESS;