У меня был проект операционных систем, в котором мне приходилось программировать интерпретатор команд в оболочке на C. Я сделал это большую часть, код, который я уже реализовал, позволяет выполнять простые команды, такие как ls
,или команды в фоновом режиме и / или с трубами.
Но теперь мне также нужно запрограммировать команду интерна (новую).Его имя будет myTime
, и оно должно позволить вам измерить время, которое требуется процессу для выполнения его функции.Например, если вы выполняете команду sleep 10
в оболочке Linux, процесс должен находиться в режиме ожидания не менее указанного времени.Цель команды интерна myTime
- измерить это время.
ВАЖНО : В коде я помогал учителям, которые позволяют мне с помощью функции под названием receive_orden получить введенную команду (например: вызов argvv [i] [0]для введенной команды i), аргументы (argvv [i] [1], первый аргумент), и если он находится или нет в фоновом режиме (bg = 0/1) Кроме того, функция pid_t fork()
создает новый процесс илиновый дочерний процесс и возвращает 0, если это дочерний процесс или pid, если он родительский.
У меня есть дополнительный код для компиляции и т. д., если он вам нужен или что-то не понятно, скажите мне.Спасибо!
Я искал в библиотеке sys / time.h и в функции gettimeofday
.Но я не смог показать сообщение, которое мне требуется в моем проекте: «Затрачено время:% f secs. \ N» Поскольку эта команда интерна должна измерять время, необходимое для выполнения процесса, я былсказал, что я должен выполнить fork () и exec () и измерить время после того, как дочерний процесс выполнил свою функцию.
Он должен отображаться так:
msh> mytime sleep 5
Time spent: 5.001719 secs
msh>
extern int obtain_order(); /* See parser.y for description */
int main(void)
{
char ***argvv;
//int command_counter;
int num_commands;
//int args_counter;
char *filev[3];
int bg;
int ret;
setenv("Acc","0",1);
setbuf(stdout, NULL); /* Unbuffered */
setbuf(stdin, NULL);
while (1)
{
fprintf(stderr, "%s", "msh> "); /* Prompt */
ret = obtain_order(&argvv, filev, &bg);
if (ret == 0) break; /* EOF */
if (ret == -1) continue; /* Syntax error */
num_commands = ret - 1; /* Line */
if (num_commands == 0) continue; /* Empty line */
if(num_commands==1){
//Implementación propia para salir del mini-shell
if(strcmp(argvv[0][0], "exit") == 0){
exit(0);
}
if(strcmp(argvv[0][0],"myTime")==0){
//HERE IS WHERE I HAVE TO IMPLEMENT THE INTERN COMMAND MYTIME
}else{ //For all other commands ls, etc... (with pipes (max 3)and background)
int pid;
int estado;
pid = fork();
switch(pid) {
case -1: /* error */
fprintf(stderr, "%s","Error en el fork del mandato simple\n");
return (-1);
case 0: /* hijo */
if (filev[0] != NULL) {
close(STDIN_FILENO);
open(filev[0],O_RDONLY);
}
if (filev[1] != NULL) {
close(STDOUT_FILENO);
open(filev[1],O_CREAT|O_WRONLY,0666);
}
if (filev[2] != NULL) {
close(STDERR_FILENO);
open(filev[2],O_CREAT|O_WRONLY,0666);
}
execvp(argvv[0][0], argvv[0]);
fprintf(stderr, "%s","Error en el execvp del mandato simple\n");
return(-1);
default: /* padre */
if(!bg){
while (wait(&estado) != pid);
}else printf("%d\n",pid);
} //fin switch (1 mandato)
} //fin if (si es comando interno o no)
}else if(num_commands==2){
int pid;
int estado;
int fd[2];
pipe(fd);
pid = fork();
switch(pid) {
case -1: /* error */
fprintf(stderr, "%s","Error en el fork del primer mandato\n");
return (-1);
case 0: /* hijo1 */
close(STDOUT_FILENO);
dup(fd[1]);
close(fd[0]);
close(fd[1]);
if (filev[0] != NULL) {
close(STDIN_FILENO);
open(filev[0],O_RDONLY);
}
if (filev[2] != NULL) {
close(STDERR_FILENO);
open(filev[2],O_CREAT|O_WRONLY,0666);
}
execvp(argvv[0][0], argvv[0]);
fprintf(stderr, "%s","Error en el execvp del primer mandato\n");
return(-1);
default: /* padre */
pid = fork();
switch(pid) {
case -1: /* error */
fprintf(stderr, "%s","Error en el fork del segundo mandato\n");
return (-1);
case 0: /* hijo 2*/
close(STDIN_FILENO);
dup(fd[0]);
close(fd[0]);
close(fd[1]);
if (filev[1] != NULL) {
close(STDOUT_FILENO);
open(filev[1],O_CREAT|O_WRONLY,0666);
}
if (filev[2] != NULL) {
close(STDERR_FILENO);
open(filev[2],O_CREAT|O_WRONLY,0666);
}
execvp(argvv[1][0], argvv[1]);
fprintf(stderr, "%s","Error en el execvp del segundo mandato\n");
return(-1);
default: /* padre */
close(fd[0]);
close(fd[1]);
if(!bg){
while (wait(&estado) != pid);
}else printf("%d\n",pid);
} //fin switch2 (2 mandatos)
} //fin switch1 (2 mandatso)
}else if(num_commands==3){
int pid;
int estado;
int fd[2], fd2[2];
pipe(fd);
pid = fork();
switch(pid) {
case -1: /* error */
fprintf(stderr, "%s","Error en el fork del primer mandato\n");
return (-1);
case 0: /* hijo1 */
close(STDOUT_FILENO);
dup(fd[1]);
close(fd[0]);
close(fd[1]);
if (filev[0] != NULL) {
close(STDIN_FILENO);
open(filev[0],O_RDONLY);
}
if (filev[2] != NULL) {
close(STDERR_FILENO);
open(filev[2],O_CREAT|O_WRONLY,0666);
}
execvp(argvv[0][0], argvv[0]);
fprintf(stderr, "%s","Error en el execvp del primer mandato\n");
return(-1);
default: /* padre */
pipe(fd2);
pid = fork();
switch(pid) {
case -1: /* error */
fprintf(stderr, "%s","Error en el fork del segundo mandato\n");
return (-1);
case 0: /* hijo 2*/
close(STDIN_FILENO);
dup(fd[0]);
close(STDOUT_FILENO);
dup(fd2[1]);
close(fd[0]);
close(fd[1]);
close(fd2[0]);
close(fd2[1]);
if (filev[2] != NULL) {
close(STDERR_FILENO);
open(filev[2],O_CREAT|O_WRONLY,0666);
}
execvp(argvv[1][0], argvv[1]);
fprintf(stderr, "%s","Error en el execvp del segundo mandato\n");
return(-1);
default: /* padre */
close(fd[0]);
close(fd[1]);
pid = fork();
switch(pid) {
case -1: /* error */
fprintf(stderr, "%s","Error en el fork del tercer mandato\n");
return (-1);
case 0: /* hijo 3*/
close(STDIN_FILENO);
dup(fd2[0]);
close(fd2[0]);
close(fd2[1]);
if (filev[1] != NULL) {
close(STDOUT_FILENO);
open(filev[1],O_CREAT|O_WRONLY,0666);
}
if (filev[2] != NULL) {
close(STDERR_FILENO);
open(filev[2],O_CREAT|O_WRONLY,0666);
}
execvp(argvv[2][0], argvv[2]);
fprintf(stderr, "%s","Error en el execvp del tercer mandato\n");
return(-1);
default: /* padre */
close(fd2[0]);
close(fd2[1]);
if(!bg){
while (wait(&estado) != pid);
}else printf("%d\n",pid);
} //fin switch 3 (3 mandatos)
} //fin switch2 (3 mandatos)
} //fin switch1 (tres mandatos)
} //fin if (número de mandatos)
} //fin while
return 0;
} //fin main