Question

In: Computer Science

Write a simple shell in C language and show some outputs.

Write a simple shell in C language and show some outputs.

Solutions

Expert Solution

PLEASE GIVE IT A THUMBS UP, I SERIOUSLY NEED ONE, IF YOU NEED ANY MODIFICATION THEN LET ME KNOW, I WILL DO IT FOR YOU

#include <stdio.h>

#include <string.h>

#include <stdlib.h>

#include <unistd.h>

#include <sys/types.h>

#include <sys/wait.h>

#include <readline/readline.h>

#include <readline/history.h>

#define MAXCOM 1000 // max number of letters to be supported

#define MAXLIST 100 // max number of commands to be supported

// Clearing the shell using escape sequences

#define clear() printf("\033[H\033[J")

// Greeting shell during startup

void init_shell()

{

    clear();

    printf("\n\n\n\n******************"

           "************************");

    printf("\n\n\n\t****MY SHELL****");

    printf("\n\n\t-USE AT YOUR OWN RISK-");

    printf("\n\n\n\n*******************"

           "***********************");

    char *username = getenv("USER");

    printf("\n\n\nUSER is: @%s", username);

    printf("\n");

    sleep(1);

    clear();
}

// Function to take input

int takeInput(char *str)

{

    char *buf;

    buf = readline("\n>>> ");

    if (strlen(buf) != 0)
    {

        add_history(buf);

        strcpy(str, buf);

        return 0;
    }
    else
    {

        return 1;
    }
}

// Function to print Current Directory.

void printDir()

{

    char cwd[1024];

    getcwd(cwd, sizeof(cwd));

    printf("\nDir: %s", cwd);
}

// Function where the system command is executed

void execArgs(char **parsed)

{

    // Forking a child

    pid_t pid = fork();

    if (pid == -1)
    {

        printf("\nFailed forking child..");

        return;
    }
    else if (pid == 0)
    {

        if (execvp(parsed[0], parsed) < 0)
        {

            printf("\nCould not execute command..");
        }

        exit(0);
    }
    else
    {

        // waiting for child to terminate

        wait(NULL);

        return;
    }
}

// Function where the piped system commands is executed

void execArgsPiped(char **parsed, char **parsedpipe)

{

    // 0 is read end, 1 is write end

    int pipefd[2];

    pid_t p1, p2;

    if (pipe(pipefd) < 0)
    {

        printf("\nPipe could not be initialized");

        return;
    }

    p1 = fork();

    if (p1 < 0)
    {

        printf("\nCould not fork");

        return;
    }

    if (p1 == 0)
    {

        // Child 1 executing..

        // It only needs to write at the write end

        close(pipefd[0]);

        dup2(pipefd[1], STDOUT_FILENO);

        close(pipefd[1]);

        if (execvp(parsed[0], parsed) < 0)
        {

            printf("\nCould not execute command 1..");

            exit(0);
        }
    }
    else
    {

        // Parent executing

        p2 = fork();

        if (p2 < 0)
        {

            printf("\nCould not fork");

            return;
        }

        // Child 2 executing..

        // It only needs to read at the read end

        if (p2 == 0)
        {

            close(pipefd[1]);

            dup2(pipefd[0], STDIN_FILENO);

            close(pipefd[0]);

            if (execvp(parsedpipe[0], parsedpipe) < 0)
            {

                printf("\nCould not execute command 2..");

                exit(0);
            }
        }
        else
        {

            // parent executing, waiting for two children

            wait(NULL);

            wait(NULL);
        }
    }
}

// Help command builtin

void openHelp()

{

    puts("\n***WELCOME TO MY SHELL HELP***"

         "\nCopyright @ Suprotik Dey"

         "\n-Use the shell at your own risk..."

         "\nList of Commands supported:"

         "\n>cd"

         "\n>ls"

         "\n>exit"

         "\n>all other general commands available in UNIX shell"

         "\n>pipe handling"

         "\n>improper space handling");

    return;
}

// Function to execute builtin commands

int ownCmdHandler(char **parsed)

{

    int NoOfOwnCmds = 4, i, switchOwnArg = 0;

    char *ListOfOwnCmds[NoOfOwnCmds];

    char *username;

    ListOfOwnCmds[0] = "exit";

    ListOfOwnCmds[1] = "cd";

    ListOfOwnCmds[2] = "help";

    ListOfOwnCmds[3] = "hello";

    for (i = 0; i < NoOfOwnCmds; i++)
    {

        if (strcmp(parsed[0], ListOfOwnCmds[i]) == 0)
        {

            switchOwnArg = i + 1;

            break;
        }
    }

    switch (switchOwnArg)
    {

    case 1:

        printf("\nGoodbye\n");

        exit(0);

    case 2:

        chdir(parsed[1]);

        return 1;

    case 3:

        openHelp();

        return 1;

    case 4:

        username = getenv("USER");

        printf("\nHello %s.\nMind that this is "

               "not a place to play around."

               "\nUse help to know more..\n",

               username);

        return 1;

    default:

        break;
    }

    return 0;
}

// function for finding pipe

int parsePipe(char *str, char **strpiped)

{

    int i;

    for (i = 0; i < 2; i++)
    {

        strpiped[i] = strsep(&str, "|");

        if (strpiped[i] == NULL)

            break;
    }

    if (strpiped[1] == NULL)

        return 0; // returns zero if no pipe is found.

    else
    {

        return 1;
    }
}

// function for parsing command words

void parseSpace(char *str, char **parsed)

{

    int i;

    for (i = 0; i < MAXLIST; i++)
    {

        parsed[i] = strsep(&str, " ");

        if (parsed[i] == NULL)

            break;

        if (strlen(parsed[i]) == 0)

            i--;
    }
}

int processString(char *str, char **parsed, char **parsedpipe)

{

    char *strpiped[2];

    int piped = 0;

    piped = parsePipe(str, strpiped);

    if (piped)
    {

        parseSpace(strpiped[0], parsed);

        parseSpace(strpiped[1], parsedpipe);
    }
    else
    {

        parseSpace(str, parsed);
    }

    if (ownCmdHandler(parsed))

        return 0;

    else

        return 1 + piped;
}

int main()

{

    char inputString[MAXCOM], *parsedArgs[MAXLIST];

    char *parsedArgsPiped[MAXLIST];

    int execFlag = 0;

    init_shell();

    while (1)
    {

        // print shell line

        printDir();

        // take input

        if (takeInput(inputString))

            continue;

        // process

        execFlag = processString(inputString,

                                 parsedArgs, parsedArgsPiped);

        // execflag returns zero if there is no command

        // or it is a builtin command,

        // 1 if it is a simple command

        // 2 if it is including a pipe.

        // execute

        if (execFlag == 1)

            execArgs(parsedArgs);

        if (execFlag == 2)

            execArgsPiped(parsedArgs, parsedArgsPiped);
    }

    return 0;
}

Related Solutions

Write the simple shell in C language. Please show some outputs.
Write the simple shell in C language. Please show some outputs.
Using C Write a program that will serve as a simple shell. This shell will execute...
Using C Write a program that will serve as a simple shell. This shell will execute an infinite for loop. In each iteration of the loop, the user will be presented with a prompt. When the user enters a command, the shell will tokenize the command, create a child process to execute it and wait for the child process to be over. If the user enters an invalid command, the shell should recognize the situation and show a meaningful message....
Create a shell in C language 1) Create an argument tokenizer then write a main() function...
Create a shell in C language 1) Create an argument tokenizer then write a main() function that prints a prompt inputed by user, accepts input, and tokenizes the input. 2) Use the argument vector to an executeCmd() function with int executeCmd(char **args); 3) The function should return a -1 if an error, or a zero otherwise. Inputing an “x” in the prompter will exit the program. 4) Write an executeCmd() function that can execute any program in the background and...
Using Virtualbox in Debian, write a simple program (a single .cpp file) in Linux shell C++...
Using Virtualbox in Debian, write a simple program (a single .cpp file) in Linux shell C++ Rules: -Use fork(), exec(), wait(), and exit() _______________________________________________________________________________________________________________________________________________ -A line of input represents a token group. -Each token group will result in the shell forking a new process and then executing the process. e.g. cat –n myfile.txt // a token group -Every token group must begin with a word that is called the command(see example above). The words immediately following a command are calledarguments(e.g....
Using Virtualbox in Debian, write a simple program (a single .cpp file) in Linux shell C++...
Using Virtualbox in Debian, write a simple program (a single .cpp file) in Linux shell C++ Rules: -Use fork(), exec(), wait(), and exit() _______________________________________________________________________________________________________________________________________________ -A line of input represents a token group. -Each token group will result in the shell forking a new process and then executing the process. e.g. cat –n myfile.txt // a token group -Every token group must begin with a word that is called the command(see example above). The words immediately following a command are calledarguments(e.g....
In C/C++ programming language, write down the lines of codes (and figure) to show- a) assignment-by-sharing...
In C/C++ programming language, write down the lines of codes (and figure) to show- a) assignment-by-sharing b) dangling reference
Write a program in assembly language that outputs the leap years between a beginning and an...
Write a program in assembly language that outputs the leap years between a beginning and an ending year. 1. Initialize $a0 and $a1 with the beginning and ending years. 2. Print out the leap years between 1970 and 2030. OUTPUT: From 1970 to 2030: 1972 … 2028
PROGRAM LANGUAGE IN C NOT C# or C++ KEEP IT SIMPLE EVEN IF IT IS REDUNDANT...
PROGRAM LANGUAGE IN C NOT C# or C++ KEEP IT SIMPLE EVEN IF IT IS REDUNDANT PLEASE. Problem: Driving Function driving(): Write a function driving(), that updates the odometer and fuel gauge of a car. The function will take in a reference to the variables storing the odometer and fuel gauge readings, along with a double representing the miles per gallon (mpg) the car gets and the number of miles the driver intends to go. The function should update the...
Perl is a programming language that can be used on Linux. Write a Perl shell script...
Perl is a programming language that can be used on Linux. Write a Perl shell script named phone.pl that prompts the user to enter first or last or any portion of person’s name, so that can be found the appropriate entry in the phone directory file called “phones”. If the user tries to enter name as the argument on the command line, he/she will get a warning message “You need to provide name when prompted by this script!” If the...
Using C as the programming language, Write a concurrent connection-oriented server that can do something simple...
Using C as the programming language, Write a concurrent connection-oriented server that can do something simple for connected clients. It should be able to carry out such processing for the client as many times as the client wants until the client indicates it wishes to end the session. The server should support multiple clients (use telnet as the client in this task). Compile and run the server program. Try and connect to it from multiple other hosts using telnet as...
ADVERTISEMENT
ADVERTISEMENT
ADVERTISEMENT