-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathglobals.c
More file actions
167 lines (136 loc) · 4.59 KB
/
globals.c
File metadata and controls
167 lines (136 loc) · 4.59 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
#include "utils.h"
#include "commands.h"
#include "prompt.h"
#include "alias.h"
#include <signal.h>
int bg_count = 0;
int log_count = 0;
int alias_count = 0;
pid_t foreground_pid = -1;
char* shell_home_directory;
static volatile int running = 1;
Alias aliases[MAX_ALIASES];
char *command_log[MAX_LOG_SIZE];
char prev_dir[PATH_MAX] = "";
ProcessInfo bg_processes[MAX_BG_PROCESSES];
void handle_error(const char *message) {
fprintf(stderr, COLOR_RED "Error: %s: %s\n" COLOR_RESET, message, strerror(errno));
}
void update_foreground_pid(pid_t new_pid) {
// Disable signals briefly if necessary to avoid race conditions
sigset_t mask, old_mask;
sigemptyset(&mask);
sigaddset(&mask, SIGCHLD); // Block SIGCHLD
sigprocmask(SIG_BLOCK, &mask, &old_mask); // Block signals
foreground_pid = new_pid;
sigprocmask(SIG_SETMASK, &old_mask, NULL); // Restore signals
}
int is_background_process(pid_t pid) {
for (int i = 0; i < bg_count; i++) {
if (bg_processes[i].pid == pid) {
return 1;
}
}
return 0;
}
void cleanup_bg_processes() {
for (int i = 0; i < bg_count; i++) {
free(bg_processes[i].command);
bg_processes[i].command = NULL; // Avoid dangling pointers
}
bg_count = 0;
}
void remove_background_process(pid_t pid) {
for (int i = 0; i < bg_count; i++) {
if (bg_processes[i].pid == pid) {
free(bg_processes[i].command);
for (int j = i; j < bg_count - 1; j++) {
bg_processes[j] = bg_processes[j + 1];
}
bg_count--;
// Only set the last command to NULL if there are remaining processes
if (bg_count > 0) {
bg_processes[bg_count].command = NULL; // Set last command to NULL
}
break;
}
}
}
void add_to_background_processes(pid_t pid, char *command) {
if (bg_count < MAX_BG_PROCESSES) {
bg_processes[bg_count].pid = pid;
bg_processes[bg_count].command = strdup(command);
if (bg_processes[bg_count].command == NULL) {
handle_error("Failed to allocate memory for background process command");
exit(EXIT_FAILURE);
}
// strcpy(bg_processes[bg_count].state, state);
bg_count++;
} else {
purge_oldest_background_commands(); // Remove the oldest background process
add_to_background_processes(pid, command); // Try again
}
}
// Purge the oldest background commands from the global array
void purge_oldest_background_commands() {
int purge_count = MAX_BG_PROCESSES / 2; // Purge the oldest 50 commands
// Shift remaining commands up by 50
for (int i = purge_count; i < bg_count; i++) {
bg_processes[i - purge_count] = bg_processes[i];
}
// Reduce the background process count
bg_count -= purge_count;
}
// Trim leading and trailing whitespace for alias processing
char* trim_whitespace_a(char *str) {
char *end;
// Trim leading space
while (isspace((unsigned char)*str)) str++;
if (*str == 0) // All spaces?
return str;
// Trim trailing space
end = str + strlen(str) - 1;
while (end > str && isspace((unsigned char)*end)) end--;
// Write new null terminator
end[1] = '\0';
return str;
}
// Function to trim whitespace from the beginning and end of a string
char *trim_whitespace(char *str) {
char *end;
// Trim leading space
while (isspace((unsigned char)*str)) str++;
// Trim trailing space
end = str + strlen(str) - 1;
while (end > str && isspace((unsigned char)*end)) end--;
end[1] = '\0'; // Null-terminate after the last non-space character
return str;
}
char* get_command_name(pid_t pid) {
char path[40];
snprintf(path, sizeof(path), "/proc/%d/comm", pid);
FILE *file = fopen(path, "r");
if (!file) {
handle_error("Failed to open /proc/pid/comm file");
return NULL;
}
char *command = malloc(256); // Allocate memory for the command name
if (fgets(command, 256, file) != NULL) {
// Remove the newline character at the end
command[strcspn(command, "\n")] = 0;
}
fclose(file);
return command;
}
// Initialize the shell home directory
void initialize_shell_home_directory() {
shell_home_directory = getcwd(NULL, 0); // Retrieve current working directory
if (!shell_home_directory) {
handle_error("Failed to get current working directory");
exit(EXIT_FAILURE);
}
}
// Check if the current directory is the home directory
int is_home_directory(const char *cwd) {
return strcmp(cwd, shell_home_directory) == 0;
}