aboutsummaryrefslogtreecommitdiff
path: root/src/Program.c
diff options
context:
space:
mode:
authordec05eba <dec05eba@protonmail.com>2020-10-30 16:47:40 +0100
committerdec05eba <dec05eba@protonmail.com>2020-10-30 18:30:46 +0100
commit928f2525c29929de0c2ab520f48c82b5cb882aa7 (patch)
treee97130909f65e7835e4740824e9f38f58e4c0fbe /src/Program.c
parente422322650f9cb057937182987071438f9c79e84 (diff)
Matrix: re-add /logout, cancel task immediately
Cancel video download when pressing escape, other fixes..
Diffstat (limited to 'src/Program.c')
-rw-r--r--src/Program.c203
1 files changed, 0 insertions, 203 deletions
diff --git a/src/Program.c b/src/Program.c
deleted file mode 100644
index a82bcd2..0000000
--- a/src/Program.c
+++ /dev/null
@@ -1,203 +0,0 @@
-#include "../include/Program.h"
-#include <unistd.h>
-#include <sys/wait.h>
-#include <sys/prctl.h>
-#include <errno.h>
-#include <string.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <assert.h>
-
-#define READ_END 0
-#define WRITE_END 1
-
-int exec_program_pipe(const char **args, ReadProgram *read_program) {
- /* 1 arguments */
- if(args[0] == NULL)
- return -1;
-
- int fd[2];
- if(pipe(fd) == -1) {
- perror("Failed to open pipe");
- return -2;
- }
-
- pid_t parent_pid = getpid();
-
- pid_t pid = fork();
- if(pid == -1) {
- perror("Failed to fork");
- close(fd[READ_END]);
- close(fd[WRITE_END]);
- return -3;
- } else if(pid == 0) { /* child */
- if(prctl(PR_SET_PDEATHSIG, SIGTERM) == -1) {
- perror("prctl(PR_SET_PDEATHSIG, SIGTERM) failed");
- _exit(127);
- }
-
- /* Test if the parent died before the above call to prctl */
- if(getppid() != parent_pid)
- _exit(127);
-
- dup2(fd[WRITE_END], STDOUT_FILENO);
- close(fd[READ_END]);
- close(fd[WRITE_END]);
-
- execvp(args[0], (char* const*)args);
- perror("execvp");
- _exit(127);
- } else { /* parent */
- close(fd[WRITE_END]);
- read_program->pid = pid;
- read_program->read_fd = fd[READ_END];
- return 0;
- }
-}
-
-int exec_program(const char **args, ProgramOutputCallback output_callback, void *userdata) {
- ReadProgram read_program;
- int res = exec_program_pipe(args, &read_program);
- if(res != 0)
- return res;
-
- int result = 0;
- int status;
-
- char buffer[4097];
-
- for(;;) {
- ssize_t bytes_read = read(read_program.read_fd, buffer, sizeof(buffer) - 1);
- if(bytes_read == 0) {
- break;
- } else if(bytes_read == -1) {
- int err = errno;
- fprintf(stderr, "Failed to read from pipe to program %s, error: %s\n", args[0], strerror(err));
- result = -err;
- break;
- }
-
- buffer[bytes_read] = '\0';
- if(output_callback) {
- result = output_callback(buffer, bytes_read, userdata);
- if(result != 0)
- break;
- }
- }
-
- if(result != 0)
- kill(read_program.pid, SIGTERM);
-
- if(waitpid(read_program.pid, &status, 0) == -1) {
- perror("waitpid failed");
- result = -5;
- goto cleanup;
- }
-
- if(!WIFEXITED(status)) {
- result = -4;
- goto cleanup;
- }
-
- int exit_status = WEXITSTATUS(status);
- if(exit_status != 0) {
- fprintf(stderr, "Failed to execute program (");
- const char **arg = args;
- while(*arg) {
- if(arg != args)
- fputc(' ', stderr);
- fprintf(stderr, "'%s'", *arg);
- ++arg;
- }
- fprintf(stderr, "), exit status %d\n", exit_status);
- result = -exit_status;
- }
-
- cleanup:
- close(read_program.read_fd);
- return result;
-}
-
-int wait_program(pid_t process_id) {
- int status;
- if(waitpid(process_id, &status, 0) == -1) {
- perror("waitpid failed");
- return -errno;
- }
-
- if(!WIFEXITED(status))
- return -4;
-
- return WEXITSTATUS(status);
-}
-
-int wait_program_non_blocking(pid_t process_id, int *status) {
- int s;
- int wait_result = waitpid(process_id, &s, WNOHANG);
- if(wait_result == -1) {
- perror("waitpid failed");
- *status = -errno;
- return 0;
- } else if(wait_result == 0) {
- /* the child process is still running */
- *status = 0;
- return 0;
- }
-
- if(!WIFEXITED(s)) {
- *status = -4;
- return 0;
- }
-
- *status = WEXITSTATUS(s);
- return 1;
-}
-
-int exec_program_async(const char **args, pid_t *result_process_id) {
- /* 1 arguments */
- if(args[0] == NULL)
- return -1;
-
- pid_t parent_pid = getpid();
-
- pid_t pid = fork();
- if(pid == -1) {
- int err = errno;
- perror("Failed to fork");
- return -err;
- } else if(pid == 0) { /* child */
- if(result_process_id) {
- if(prctl(PR_SET_PDEATHSIG, SIGTERM) == -1) {
- perror("prctl(PR_SET_PDEATHSIG, SIGTERM) failed");
- _exit(127);
- }
-
- /* Test if the parent died before the above call to prctl */
- if(getppid() != parent_pid)
- _exit(127);
-
- execvp(args[0], (char* const*)args);
- perror("execvp");
- _exit(127);
- } else {
- setsid();
- signal(SIGHUP, SIG_IGN);
-
- // TODO: Still creates zombie??? find a fix!
-
- // Daemonize child to make the parent the init process which will reap the zombie child
- pid_t second_child = fork();
- if(second_child == 0) { // child
- execvp(args[0], (char* const*)args);
- perror("execvp");
- _exit(127);
- } else if(second_child != -1) {
- _exit(0);
- }
- }
- } else { /* parent */
- if(result_process_id)
- *result_process_id = pid;
- }
- return 0;
-}