1 /* 2 * Copyright (C) 2025 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 #ifndef _LIBC_TEST_FUNCTIONALEXT_ADLT_H_ 16 #define _LIBC_TEST_FUNCTIONALEXT_ADLT_H_ 17 18 #include <cstdio> 19 #include <cstdlib> 20 21 #include <string> 22 #include <functional> 23 #include <fstream> 24 #include <sstream> 25 26 #include <sys/types.h> 27 #include <sys/wait.h> 28 #include <unistd.h> 29 #include <fcntl.h> 30 31 #include "functionalext.h" 32 33 #define EXEC_STATEMENT(pipe_out, statement) { \ 34 close((pipe_out)[0]); \ 35 dup2((pipe_out)[1], STDOUT_FILENO); \ 36 dup2((pipe_out)[1], STDERR_FILENO); \ 37 close((pipe_out)[1]); \ 38 (statement); \ 39 fflush(stdout); \ 40 fflush(stderr); \ 41 exit(errno); \ 42 } 43 44 #define WAIT_AND_CMP_OUTPUT(func, pipe_out, expect_ret, expect_output) { \ 45 close((pipe_out)[1]); \ 46 std::string str = read_pipe((pipe_out)[0]); \ 47 close((pipe_out)[0]); \ 48 wait_process(pid, expect_ret); \ 49 if (memcmp((expect_output), str.c_str(), str.size())) { \ 50 t_error("%s: output mismatch: (%s) (%s)\n", (func), (expect_output), str.c_str()); \ 51 } \ 52 } 53 54 #define EXPECT_EXIT(func, statement, expect_ret, expect_output) { \ 55 int pipe_out[2]; \ 56 if (pipe(pipe_out) < 0) { t_error("%s: Failed create pipe\n", (func)); } \ 57 else { \ 58 pid_t pid = fork(); \ 59 if (pid == 0) { EXEC_STATEMENT(pipe_out, statement); } \ 60 else if (pid > 0) { WAIT_AND_CMP_OUTPUT(func, pipe_out, expect_ret, expect_output); } \ 61 else { t_error("%s: failed to fork child process\n", (func)); } \ 62 } \ 63 } 64 65 std::string read_pipe(int pipe_id); 66 int wait_process(int pid, int expect_ret = 0); 67 int run_subprocess(std::function<void()> func, int &child_pid); 68 int run_subprocess(std::function<void()> func, int &child_pid, const std::string &file); 69 int run_self_command(const std::string &args, const std::string &env = ""); 70 71 #endif