|
|||||||
|
|
|
![]() |
|
|
Strumenti |
|
|
#1 |
|
Senior Member
Iscritto dal: Nov 2004
Messaggi: 409
|
[C]:minishell
Ciao ragazzi ho bisogno di un aiuto con questo esercizio :
Scrivere una mini schell che iterativamente legge una riga di testo ed esegue il suo contenuto in un processo dedicato (attendendo la terminazione di questo processo). La shell termina col comando stop. (Suggerimenti: per la lettura della linea di comando si puo usare la funzione della libreria c fgets). Questo è il codice che fino ad ora ho prodotto: Codice:
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
int main (int argc, char *argv[]){
int pid;
int status;
char *stringa;
stringa=calloc(20,sizeof(char));
if ((stringa=fgets(stringa,20,stdin)) == NULL) exit(1);
while ( strncmp(stringa,"stop",4) != 0){
if ( (pid = fork()) < 0){
perror("fork");
exit(1);
}else{
if (pid == 0){//figlio
if ( execlp(stringa,stringa,(char *)0) < 0 )
perror("execlp"),exit(1);
}else{//padre
//aspetto la terminazione di mio figlio
wait(&status);
}//fine else padre
}//fine else
if ((stringa=fgets(stringa,20,stdin)) == NULL) exit(1);
}//fine while
exit (0);
}
Grazie per l'attenzione. |
|
|
|
|
|
#2 |
|
Senior Member
Iscritto dal: Jul 2005
Città: Bologna
Messaggi: 1130
|
Dai un'occhiata qui: http://www.advancedlinuxprogramming.com/alp-folder
E' un ottimo libro, ed è g-r-a-t-i-s!
__________________
-> The Motherfucking Manifesto For Programming, Motherfuckers |
|
|
|
|
|
#3 | |
|
Senior Member
Iscritto dal: Nov 2005
Città: TO
Messaggi: 5206
|
Quote:
Per la execlp, ti dico subito che dovresti gestire la cosa in modo un po' diverso. Ognuna delle funzioni execXX (ce ne sono ben 5) si aspetta un certo numero di parametri da passare all'nuovo processo. Le exec con la "l" si aspettano una lista di argomenti terminata da un NULL, mentre le exec con la "v" si aspettano un array di char* il cui ultimo elemento è un NULL. Se in input prendi la stringa "ls -la /etc", dovresti spezzare tu in qualche modo la stringa in modo da ottenere N stringhe, ad esempio: "ls", "-la" e "/etc". La prima stringa è il primo parametro (il nome del programma) da passare alla exec e le restanti stringhe sono gli argomenti. Qundi credo che sia molto meglio usare una delle exec che accetta un array. Creare un array è facile e ti risolve brillantemente il problema.
__________________
Andrea, SCJP 5 (91%) - SCWCD 5 (94%) |
|
|
|
|
|
|
#4 | |
|
Senior Member
Iscritto dal: Nov 2004
Messaggi: 409
|
Quote:
Si infatti ci avevo pensato, solo che speravo ci fosse un modo più semplice oppure che si potesse eseguire direttamente tutta la stringa. Grazie per l'aiuto e per la disponibilità,ciao |
|
|
|
|
|
|
#5 | |
|
Senior Member
Iscritto dal: Nov 2005
Città: TO
Messaggi: 5206
|
Quote:
__________________
Andrea, SCJP 5 (91%) - SCWCD 5 (94%) |
|
|
|
|
|
|
#6 |
|
Senior Member
Iscritto dal: Nov 2004
Messaggi: 409
|
Mi potreste dare una mano nell'allocazione di un array di stringhe?Ciao e grazie
|
|
|
|
|
|
#7 | |
|
Senior Member
Iscritto dal: Nov 2005
Città: TO
Messaggi: 5206
|
Quote:
Mi spiego meglio: se hai in input una stringa lunga al massimo 40 caratteri, supponendo di avere 1 car., 1 spazio, 1 car., ecc..., risulta che puoi avere al massimo 20 parametri. Ora, 20 parametri sono pochi e l'array lo si potrebbe dichiarare (senza fare nemmeno allocazioni dinamiche) come: Codice:
char *stringhe[21]; /* uno in più per il NULL finale */ Insomma, dipende molto da come vuoi gestire il numero dei parametri.
__________________
Andrea, SCJP 5 (91%) - SCWCD 5 (94%) |
|
|
|
|
|
|
#8 | |
|
Senior Member
Iscritto dal: Nov 2004
Messaggi: 409
|
Quote:
|
|
|
|
|
|
|
#9 | |
|
Senior Member
Iscritto dal: Nov 2005
Città: TO
Messaggi: 5206
|
Quote:
Io ad esempio farei così: una struttura Codice:
typedef struct
{
char **strings;
int size;
int capacity;
} STRING_ARRAY;
Poi tutta la "logica" di (ri)allocazione dell'array è da fare ovviamente! Pensaci un po', poi al massimo butto giù (appena ho tempo) del codice.
__________________
Andrea, SCJP 5 (91%) - SCWCD 5 (94%) |
|
|
|
|
|
|
#10 |
|
Senior Member
Iscritto dal: Nov 2004
Messaggi: 409
|
Ho fatto in questo modo, sembra funzionare. Mentre se utilizzo la funzione dealloca, che adesso è commentata nel codice, non funziona.Qualcuno ha idea di quale sia il motivo?????
Codice:
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
char **crea_vettore(char *stringa);
void dealloca(char **array_di_stringhe);
int main (int argc, char *argv[]){
int pid,i;
int status;
char *stringa;//stringa dove memorizzo la stringa dei comandi
char **stringhe; //array di stringhe
stringa=(char *)calloc(20,sizeof(char));
if ((stringa=fgets(stringa,20,stdin)) == NULL) exit(1);
while ( strncmp(stringa,"stop",4) != 0){
stringhe=crea_vettore(stringa);
if ( (pid = fork()) < 0){
perror("fork");
exit(1);
}else{
if (pid == 0){//figlio
if ( execvp(stringhe[0],stringhe) < 0 )
perror("execvp"),exit(1);
}else{//padre
//aspetto la terminazione di mio figlio
wait(&status);
//dealloca(stringhe);//libero memoria
}//fine else padre
}//fine else
if ((stringa=fgets(stringa,20,stdin)) == NULL) exit(1);
}//fine while
exit (0);
}
char **crea_vettore(char *stringa){
char **stringhe;
char *parola=NULL;
int i=0,
size=1,
j=0;
if ((stringhe=(char **)malloc(size*sizeof(char *))) == NULL)
perror("malloc"),exit(1);//errore allocazione
while ( stringa[i] != '\0' ){//scandisco tutta la stringa e la divido in tante parole
while ( (stringa[i] != ' ') && (stringa[i] != '\0') && (stringa[i] != '\n')){
//costruisco la parola
parola=(char *)realloc(parola,(j+1)*sizeof(char *));
parola[j]=stringa[i];
j=j+1;
i=i+1;
}
if ( ( stringa[i] == ' ') || (stringa[i] == '\n') )
i=i+1;
printf("parola= %s\n",parola);
if (parola != NULL){//parola trovata
stringhe=(char **)realloc(stringhe,(size+1)*sizeof(char *));
if ( (stringhe[size-1]=(char *)malloc(strlen(parola)+1)) == NULL)
perror("malloc"),exit(1);//errore allocazione
strcpy(stringhe[size-1],parola);
size=size+1;
}
parola=NULL;
j=0;
}
stringhe[size-1]=NULL;//fine dell array di stringhe
return (stringhe);
}
void dealloca(char **array_di_stringhe){
int i=0;
while ( array_di_stringhe[i] != NULL ){
free(array_di_stringhe[i]);
i=i+1;
}
free(array_di_stringhe[i]);
free(array_di_stringhe);
return;
}
|
|
|
|
|
| Strumenti | |
|
|
Tutti gli orari sono GMT +1. Ora sono le: 08:50.



















