#include <stdio.h>
#include <stdlib.h>
#include <getopt.h>
#include <stdbool.h>
#include <string.h>
#include <strings.h>
#include <unistd.h>
#include <sys/wait.h>
#include <sys/types.h>
#include <dirent.h>
#ifndef PATH_MAX
#define PATH_MAX 255
#endif
void search(char* path, char* name, bool rekursiv, bool caseSensitive);
int main(int argc, char *argv[]){
bool rekursiv = false;
bool caseSensitive = true;
int indexOfPath = 0;
int indexOfR = 0;
int indexOfI = 0;
int sumChild = 0;
char* relPath;
char* absolutePath;
pid_t pid = 0;
//Falls zu wenig Einträge, gib Fehler aus
if(argc < 3){
perror("Wrong usage! Input:
/myfind [-R] [-i] searchpath filename1 [filename2] …[filenamen]");
return 1;
}
//Gehe durch die mitgegebenen Argumente und
//setze die Variablen die man benötigt für weiteren Programmverlauf
for(int i = 1; i < argc; i++){
if(strcmp(argv[i], "-R") == 0){
rekursiv = true;
indexOfR = i;
}
else if(strcmp(argv[i], "-i") == 0){
caseSensitive = false;
indexOfI = i;
}
else if(indexOfPath == 0){
indexOfPath = i;
}
}
//gehe durch alle gewünschen Sucheinträge und spalte einen Prozess
//ab der nach jeden Eintrag eigenständig sucht.
for(int i = 1; i < argc; i++){
if(i != indexOfPath && i != indexOfI && i != indexOfR){
switch(pid = fork()){
case -1:
perror("Fehler bei fork()!");
return -2;
break;
case 0:
//Rückgabewert von Kindprozess
relPath = argv[indexOfPath];
realpath(relPath, absolutePath);
//printf("%s\n", absolutePath);
search(absolutePath, argv[i], rekursiv, caseSensitive);
return 0;
break;
default:
sumChild ++;
break;
}
}
}
int status;
while(sumChild > 0){
pid = wait(&status);
sumChild --;
}
return 0;
}
void search(char* path, char* name, bool rekursiv, bool caseSensitive){
DIR * d = opendir(path);
pid_t pid = getpid();
//überprüfen ob der Eintrag NULL ist, falls ja wird abgebrochen
if(d == NULL){;
return;
}
struct dirent * dir;
//Solange der aktuelle Folder nicht lerr ist, suche durch
while((dir = readdir(d)) != NULL) {
//Checke ob die aktuelle überprüfende Datei ein Ordner oder Datei ist.
if(dir-> d_type != DT_DIR){
//Checke ob caseSensitive flag gesetzt ist oder nicht,
//falls ja compare string 1:1
if(caseSensitive){
if((strcmp(dir->d_name, name) == 0)){
printf("%ld : %s : %s/%s\n", (long) pid, name, path, name);
}
//Falls caseSensitive nicht erwünscht ist, ignoriere es und vergleiche
}else{
if((strcasecmp(dir->d_name, name) == 0)){
printf("%ld : %s : %s/%s\n", (long) pid, name, path, dir->d_name);
}
}
//Ist die aktuelle Date ein Ordner,
//überprüfe auf namen beziehungsweise ob rekursiv Flag gesetzt ist.
}else if(dir->d_type == DT_DIR &&
strcmp(dir->d_name, ".") != 0 &&
strcmp(dir->d_name, "..") != 0 && rekursiv == true){
char d_path[PATH_MAX];
//Wenn eingegebene Path nur Root "/"
//ist dann einfach ohne / zusammenfügen
if(strcmp(path, "/") == 0 ){
sprintf(d_path, "%s%s", path, dir->d_name);
}
//Wenn eingegebene Path bereits Elemente außer Root enthält,
//füge mit / die Elemente zusammen
else{
sprintf(d_path, "%s/%s", path, dir->d_name);
}
//geh rekursiv in die Funtktion ob weiterzusuchen falls man sich
//in einen neuen Ordner befindet.
search(d_path, name, rekursiv, caseSensitive);
}
}
//Schließe die offene directory
closedir(d);
}
Comments