Implémentation des premiers opérateurs

This commit is contained in:
Antoine Bartuccio 2017-05-16 19:15:51 +02:00
parent b33f1ef973
commit 2bf5af245c
8 changed files with 170 additions and 45 deletions

View File

@ -47,7 +47,10 @@ include_directories(
set(CMAKE_C_STANDARD 99)
set(CMAKE_C_FLAGS "-Wall -Werror -pedantic -fpic -Wextra -Wshadow")
add_subdirectory(fish_shell)
set(SOURCE_FILES fish_shell/main.c fish_shell/fish_types.h fish_shell/fish_core.h fish_shell/fish_core.c fish_shell/fish_commands.c fish_shell/fish_commands.h fish_shell/fish_globbing.c fish_shell/fish_globbing.h fish_shell/fish_utils.c fish_shell/fish_utils.h)
add_executable(fish ${SOURCE_FILES})
#add_subdirectory(fish_shell)
add_subdirectory(fish_shell_tests)

View File

@ -1,8 +0,0 @@
cmake_minimum_required(VERSION 3.7)
project(fish_shell)
set(CMAKE_C_STANDARD 99)
set(CMAKE_C_FLAGS "-Wall -Werror -pedantic -fpic -Wextra -Wshadow")
set(SOURCE_FILES main.c fish_types.h fish_core.h fish_core.c fish_commands.c fish_commands.h fish_globbing.c fish_globbing.h fish_utils.c fish_utils.h)
add_executable(fish ${SOURCE_FILES})

View File

@ -3,7 +3,9 @@
//
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include "fish_core.h"
#include "fish_types.h"
/* Necessary global variables */
char * builtinCommandsStr[] = {
@ -35,11 +37,12 @@ int fishCd(WordArray *args) {
perror("fish");
}
}
return 1;
return 0;
}
int fishHelp(WordArray *args) {
int i;
args->size = args->size;
printf("Bartuccio Antoine, Amalvy Arthur, Yann Chevanton\n");
printf("Tape tes putains de noms de programmes et tes arguments de merde et tabasse ENTER !\n");
printf("Les commandes suivantes sont internes :\n");
@ -47,16 +50,13 @@ int fishHelp(WordArray *args) {
printf("\t%s\n", builtinCommandsStr[i]);
}
printf("Et sinon pour le reste, RTFM !");
if (args->size > 0)
return 1;
return 1;
return 0;
}
int fishExit(WordArray *args) {
if (args->size != 1)
return 1;
else
return 0;
args->size = args->size;
exit(EXIT_SUCCESS);
}
int getNbBuiltins() {

View File

@ -9,11 +9,11 @@
#include <sys/wait.h>
#include "fish_core.h"
#include "fish_globbing.h"
#include "fish_types.h"
void fishLoop(Settings * settings){
char * line = NULL;
WordList* splited = NULL;
WordArray* array = NULL;
int status = 1;
do {
@ -23,11 +23,10 @@ void fishLoop(Settings * settings){
splited = split(line, (char*) FISH_TOKENS);
splited = fishExpand(splited);
array = wordListToWordArray(splited);
status = fishExecute(array);
status = fishExecute(splited);
freeWordArray(array);
free(line);
} while(status);
}
@ -124,16 +123,16 @@ void freeSettings(Settings *settings){
int fishLoad(WordArray *array) {
pid_t pid;
int status;
int status = 1;
pid = fork();
if (pid == 0){
/* Executes only in the child process */
if (execvp(array->words[0], array->words) == -1){
/* Error during system call */
perror("fish");
exit(EXIT_FAILURE);
}
exit(EXIT_FAILURE);
exit(EXIT_SUCCESS);
} else if (pid < 0){
/* Fork failed */
perror("fish");
@ -144,21 +143,66 @@ int fishLoad(WordArray *array) {
do {
waitpid(pid, &status, WUNTRACED);
} while (!WIFEXITED(status) && !WIFSIGNALED(status));
if (status) fprintf(stderr, "%s\n", getInsult());
}
return status;
}
int fishExecute(WordList *list) {
WordList *splited = NULL;
shell_operator op = NONE;
WordArray *array = NULL;
splited = parseWordList(list, &op);
array = wordListToWordArray(list);
switch (op) {
case AND:
if (!loadRightCommand(array)) fishExecute(splited);
else freeWordList(splited);
break;
case OR:
loadRightCommand(array);
fishExecute(splited);
break;
default:
loadRightCommand(array);
}
return 1;
}
int fishExecute(WordArray *array) {
int loadRightCommand(WordArray *array){
int i;
if (array->size < 0)
return 1;
for (i=0; i < getNbBuiltins(); i++){
if (!strcmp(array->words[0], getBuiltinCommandsStr()[i])){
if (array->size <= 0) return 1;
for (i = 0; i < getNbBuiltins(); i++) {
if (!strcmp(array->words[0], getBuiltinCommandsStr()[i])) {
return getBuiltinCommands()[i](array);
}
}
return fishLoad(array);
}
WordList * parseWordList(WordList *list, shell_operator *an_operator) {
char *op_str[] = {
(char*) "&&",
(char*) "||"
};
shell_operator op[] = {
AND,
OR
};
WordList *newList = NULL;
int max = sizeof(op_str) / sizeof(char*);
int i = 0;
while (i < max && newList == NULL){
newList = splitWordList(list, op_str[i]);
i++;
}
if (newList != NULL) *an_operator = op[i-1];
else *an_operator = NONE;
return newList;
}

View File

@ -32,9 +32,12 @@ char * fishReadLine();
int countSeparators(char *string, char *separators); // Tested
int fishLoad(WordArray *array);
int fishExecute(WordArray *array);
int fishExecute(WordList *list);
WordList *parseWordList(WordList *list, shell_operator *an_operator);
int loadRightCommand(WordArray *array);
#endif //FISH_FISH_CORE_H

View File

@ -7,6 +7,14 @@
/* Custom types */
typedef enum {
NONE,
PIPE,
BACKGROUND_PROCESS,
AND,
OR
} shell_operator ;
typedef struct {
char ** words;
int size;

View File

@ -6,6 +6,7 @@
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include "fish_utils.h"
#include "fish_types.h"
void crash(){
@ -30,7 +31,11 @@ char *getInsult(){
char *insults[] = {
(char *) "Apprend à écrire crétin !",
(char *) "Bolos !",
(char *) "Mois aussi je sais écrire de la merde, pourtant je le fait pas !"
(char *) "Mois aussi je sais écrire de la merde, pourtant je le fait pas !",
(char *) "Oh ! Une erreur ! Comme ta vie en fait...",
(char *) "Nul !",
(char *) "Pense à aller à l'école un jour",
(char *) "Et après on dit que c'est la faute de l'ordinateur..."
};
if (!init){
srand((unsigned int) time(NULL));
@ -84,20 +89,11 @@ void addWordList(WordList *list, char *word) {
}
void removeWordList(WordList *list) {
WordListElement *current = list->last;
if (current != NULL){
list->last = current->previous;
if (current->previous != NULL)
current->previous->next = NULL;
if (current->word != NULL)
free(current->word);
free(current);
list->size--;
}
if (list != NULL) removeWordListElem(list, list->last);
}
void freeWordList(WordList *list) {
while (list->size != 0)
while (list != NULL && list->size != 0)
removeWordList(list);
free(list);
}
@ -138,3 +134,76 @@ WordList *wordArrayToWordList(WordArray *array) {
return list;
}
void removeWordListElem(WordList *list, WordListElement *elem) {
if (list != NULL && elem != NULL){
if (list->first == elem && list->last == elem){
list->first = NULL;
list->last = NULL;
} else if (list->first == elem){
list->first = elem->next;
elem->previous = NULL;
} else if (list->last == elem){
list->last = elem->previous;
elem->previous->next = NULL;
} else {
elem->next->previous = elem->previous;
elem->previous->next = elem->next;
}
list->size--;
if (elem->word != NULL)
free(elem->word);
free(elem);
}
}
WordList *sliceWordList(WordList *list, int min_index, int max_index) {
WordList *newList = createWordList();
WordListElement *elem = NULL;
WordListElement *tmp = NULL;
int i=0;
if (list == NULL || min_index > list->size || max_index > list->size) return newList;
else {
elem = list->first;
while (i < max_index){
tmp = elem->next;
if (i >= min_index){
addWordList(newList, elem->word);
removeWordListElem(list, elem);
}
elem = tmp;
i++;
}
}
return newList;
}
WordList *splitWordList(WordList *list, char *token) {
WordList * newList = NULL;
WordListElement * current = list->first;
int i = 0;
while (current != NULL){
if (!strcmp(current->word, token)){
newList = sliceWordList(list, i + 1, list->size);
removeWordListElem(list, current);
current = NULL;
}
else current = current->next;
i++;
}
return newList;
}

View File

@ -15,14 +15,20 @@ void freeWordArray(WordArray *array); // Tested
WordList * createWordList(); // Tested
WordList * sliceWordList(WordList *list, int min_index, int max_index);
void addWordList(WordList *list, char *word); // Tested
void removeWordList(WordList *list); // Tested
void removeWordListElem(WordList *list, WordListElement *elem);
void freeWordList(WordList *list); // Tested
WordArray * wordListToWordArray(WordList *list); // Tested
WordList * wordArrayToWordList(WordArray * array); // Tested
WordList * splitWordList(WordList *list, char * tokens);
#endif //FISH_FISH_UTILS_H