-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathimage_filter.c
executable file
·140 lines (114 loc) · 4.44 KB
/
image_filter.c
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
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <fcntl.h>
#include <unistd.h>
#include "bitmap.h"
#define ERROR_MESSAGE "Warning: one or more filter had an error, so the output image may not be correct.\n"
#define SUCCESS_MESSAGE "Image transformed successfully!\n"
/*
* Check whether the given command is a valid image filter, and if so,
* run the process.
*
* We've given you this function to illustrate the expected command-line
* arguments for image_filter. No further error-checking is required for
* the child processes.
*/
void run_command(const char *cmd) {
if (strcmp(cmd, "copy") == 0 || strcmp(cmd, "./copy") == 0 ||
strcmp(cmd, "greyscale") == 0 || strcmp(cmd, "./greyscale") == 0 ||
strcmp(cmd, "gaussian_blur") == 0 || strcmp(cmd, "./gaussian_blur") == 0 ||
strcmp(cmd, "edge_detection") == 0 || strcmp(cmd, "./edge_detection") == 0) {
execl(cmd, cmd, NULL);
} else if (strncmp(cmd, "scale", 5) == 0) {
// Note: the numeric argument starts at cmd[6]
execl("scale", "scale", cmd + 6, NULL);
} else if (strncmp(cmd, "./scale", 7) == 0) {
// Note: the numeric argument starts at cmd[8]
execl("./scale", "./scale", cmd + 8, NULL);
} else {
fprintf(stderr, "Invalid command '%s'\n", cmd);
exit(1);
}
}
// TODO: Complete this function.
int main(int argc, char **argv) {
if (argc < 3) {
printf("Usage: image_filter input output [filter ...]\n");
exit(1);
}
// If only 3 arguements are provided, just copy image to stdout
else if(argc == 3) {
// Create a pipe
int fd[2]; //array of two file descriptors (for reading and writing)
pipe(fd);
int file1 = open(argv[1], O_RDWR);
int file2 = open(argv[2], O_RDWR);
int r = fork();
if(r == 0) { //ie. child
dup2(file1, fileno(stdin)); // redirect the standard input to file1
dup2(file2, fileno(stdout)); //redirect standard outout to file2
close(fd[0]);
close(fd[1]);
run_command("./copy");
exit(0);
}
else if(r > 0) { //ie parent
close(fd[0]);
close(fd[1]);
int exit_status;
int status;
if(wait(&status) != -1) {
if (WIFEXITED(status)) {
exit_status = WEXITSTATUS(status);
if (exit_status == 0) {
printf(SUCCESS_MESSAGE);
}
else {
printf(ERROR_MESSAGE);
}
}
}
}
}
// else we need to loop through all the arguements provided and apply filter
else {
for(int i = 3; i < argc + 1; i++) {
int file1 = open(argv[1], O_RDWR);
int file2 = open(argv[2], O_RDWR);
int fds[2]; //array of two file descriptors (for reading and writing)
pipe(fds);
int r = fork();
if(r == 0) { //ie. child
dup2(file1, fileno(stdin)); // redirect the standard input to file1
dup2(file2, fileno(stdout)); //redirect standard outout to file2
close(fds[0]);
close(fds[1]);
char *filter = argv[i];
run_command(filter);
}
else if(r > 0) { //ie parent
close(fds[0]);
close(fds[1]);
int exit_status;
int status;
if(wait(&status) != -1) {
if (WIFEXITED(status)) {
exit_status = WEXITSTATUS(status);
if (exit_status == 0) {
printf(SUCCESS_MESSAGE);
exit(0);
}
else {
printf(ERROR_MESSAGE);
exit(1);
}
}
}
}
}
}
return 0;
}