Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/app/bdsh/input.c

    rb48d046 r5db9084  
    1 /*
    2  * Copyright (c) 2008 Tim Post
    3  * Copyright (c) 2011 Jiri Svoboda
    4  * Copyright (c) 2011 Martin Sucha
     1/* Copyright (c) 2008, Tim Post <tinkertim@gmail.com>
    52 * All rights reserved.
    63 *
    74 * Redistribution and use in source and binary forms, with or without
    8  * modification, are permitted provided that the following conditions
    9  * are met:
     5 * modification, are permitted provided that the following conditions are met:
    106 *
    11  * - Redistributions of source code must retain the above copyright
    12  *   notice, this list of conditions and the following disclaimer.
    13  * - Redistributions in binary form must reproduce the above copyright
    14  *   notice, this list of conditions and the following disclaimer in the
    15  *   documentation and/or other materials provided with the distribution.
    16  * - The name of the author may not be used to endorse or promote products
    17  *   derived from this software without specific prior written permission.
     7 * Redistributions of source code must retain the above copyright notice, this
     8 * list of conditions and the following disclaimer.
    189 *
    19  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
    20  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
    21  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
    22  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
    23  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
    24  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
    25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
    26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
    27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
    28  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     10 * Redistributions in binary form must reproduce the above copyright notice,
     11 * this list of conditions and the following disclaimer in the documentation
     12 * and/or other materials provided with the distribution.
     13 *
     14 * Neither the name of the original program's authors nor the names of its
     15 * contributors may be used to endorse or promote products derived from this
     16 * software without specific prior written permission.
     17 *
     18 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
     19 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     20 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     21 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
     22 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     23 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     24 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     25 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     26 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     27 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     28 * POSSIBILITY OF SUCH DAMAGE.
    2929 */
    3030
     
    4545
    4646#include "config.h"
    47 #include "compl.h"
    4847#include "util.h"
    4948#include "scli.h"
     
    5150#include "errors.h"
    5251#include "exec.h"
    53 #include "tok.h"
    5452
    5553extern volatile unsigned int cli_quit;
     
    5856static tinput_t *tinput;
    5957
    60 /* Private helpers */
    61 static int run_command(char **, cliuser_t *, iostate_t *);
    62 static void print_pipe_usage(void);
    63 
    6458/* Tokenizes input from console, sees if the first word is a built-in, if so
    6559 * invokes the built-in entry point (a[0]) passing all arguments in a[] to
    6660 * the handler */
    67 int process_input(cliuser_t *usr)
     61int tok_input(cliuser_t *usr)
    6862{
    69         token_t *tokens = calloc(WORD_MAX, sizeof(token_t));
    70         if (tokens == NULL)
    71                 return ENOMEM;
    72        
    7363        char *cmd[WORD_MAX];
     64        int n = 0, i = 0;
    7465        int rc = 0;
    75         tokenizer_t tok;
    76         unsigned int i, pipe_count, processed_pipes;
    77         unsigned int pipe_pos[2];
    78         char *redir_from = NULL;
    79         char *redir_to = NULL;
     66        char *tmp;
    8067
    81         if (usr->line == NULL) {
    82                 free(tokens);
     68        if (NULL == usr->line)
    8369                return CL_EFAIL;
     70
     71        tmp = str_dup(usr->line);
     72
     73        cmd[n] = strtok(tmp, " ");
     74        while (cmd[n] && n < WORD_MAX) {
     75                cmd[++n] = strtok(NULL, " ");
    8476        }
    8577
    86         rc = tok_init(&tok, usr->line, tokens, WORD_MAX);
    87         if (rc != EOK) {
     78        /* We have rubbish */
     79        if (NULL == cmd[0]) {
     80                rc = CL_ENOENT;
    8881                goto finit;
    8982        }
    90        
    91         size_t tokens_length;
    92         rc = tok_tokenize(&tok, &tokens_length);
    93         if (rc != EOK) {
     83
     84        /* Its a builtin command ? */
     85        if ((i = (is_builtin(cmd[0]))) > -1) {
     86                rc = run_builtin(i, cmd, usr);
     87                goto finit;
     88        /* Its a module ? */
     89        } else if ((i = (is_module(cmd[0]))) > -1) {
     90                rc = run_module(i, cmd);
    9491                goto finit;
    9592        }
    96        
    97         if (tokens_length > 0 && tokens[0].type == TOKTYPE_SPACE) {
    98                 tokens++;
    99                 tokens_length--;
    100         }
    101        
    102         if (tokens_length > 0 && tokens[tokens_length-1].type == TOKTYPE_SPACE) {
    103                 tokens_length--;
    104         }
    105        
    106         /* Until full support for pipes is implemented, allow for a simple case:
    107          * [from <file> |] command [| to <file>]
    108          *
    109          * First find the pipes and check that there are no more
    110          */
    111         for (i = 0, pipe_count = 0; i < tokens_length; i++) {
    112                 if (tokens[i].type == TOKTYPE_PIPE) {
    113                         if (pipe_count >= 2) {
    114                                 print_pipe_usage();
    115                                 rc = ENOTSUP;
    116                                 goto finit;
    117                         }
    118                         pipe_pos[pipe_count] = i;
    119                         pipe_count++;
    120                 }
    121         }
    122        
    123         unsigned int cmd_token_start = 0;
    124         unsigned int cmd_token_end = tokens_length;
    125        
    126         processed_pipes = 0;
    127        
    128         /* Check if the first part (from <file> |) is present */
    129         if (pipe_count > 0 && (pipe_pos[0] == 3 || pipe_pos[0] == 4) && str_cmp(tokens[0].text, "from") == 0) {
    130                 /* Ignore the first three tokens (from, file, pipe) and set from */
    131                 redir_from = tokens[2].text;
    132                 cmd_token_start = pipe_pos[0]+1;
    133                 processed_pipes++;
    134         }
    135        
    136         /* Check if the second part (| to <file>) is present */
    137         if ((pipe_count - processed_pipes) > 0 &&
    138             (pipe_pos[processed_pipes] == tokens_length - 4 ||
    139             (pipe_pos[processed_pipes] == tokens_length - 5 &&
    140             tokens[tokens_length-4].type == TOKTYPE_SPACE )) &&
    141             str_cmp(tokens[tokens_length-3].text, "to") == 0) {
    142                 /* Ignore the last three tokens (pipe, to, file) and set to */
    143                 redir_to = tokens[tokens_length-1].text;
    144                 cmd_token_end = pipe_pos[processed_pipes];
    145                 processed_pipes++;
    146         }
    147        
    148         if (processed_pipes != pipe_count) {
    149                 print_pipe_usage();
    150                 rc = ENOTSUP;
    151                 goto finit;
    152         }
    153        
    154         /* Convert tokens of the command to string array */
    155         unsigned int cmd_pos = 0;
    156         for (i = cmd_token_start; i < cmd_token_end; i++) {
    157                 if (tokens[i].type != TOKTYPE_SPACE) {
    158                         cmd[cmd_pos++] = tokens[i].text;
    159                 }
    160         }
    161         cmd[cmd_pos++] = NULL;
    162        
    163         if (cmd[0] == NULL) {
    164                 print_pipe_usage();
    165                 rc = ENOTSUP;
    166                 goto finit;
    167         }
    168        
    169         iostate_t new_iostate = {
    170                 .stdin = stdin,
    171                 .stdout = stdout,
    172                 .stderr = stderr
    173         };
    174        
    175         FILE *from = NULL;
    176         FILE *to = NULL;
    177        
    178         if (redir_from) {
    179                 from = fopen(redir_from, "r");
    180                 if (from == NULL) {
    181                         printf("Cannot open file %s\n", redir_from);
    182                         rc = errno;
    183                         goto finit_with_files;
    184                 }
    185                 new_iostate.stdin = from;
    186         }
    187        
    188        
    189         if (redir_to) {
    190                 to = fopen(redir_to, "w");
    191                 if (to == NULL) {
    192                         printf("Cannot open file %s\n", redir_to);
    193                         rc = errno;
    194                         goto finit_with_files;
    195                 }
    196                 new_iostate.stdout = to;
    197         }
    198        
    199         rc = run_command(cmd, usr, &new_iostate);
    200        
    201 finit_with_files:
    202         if (from != NULL) {
    203                 fclose(from);
    204         }
    205         if (to != NULL) {
    206                 fclose(to);
    207         }
    208        
     93
     94        /* See what try_exec thinks of it */
     95        rc = try_exec(cmd[0], cmd);
     96
    20997finit:
    21098        if (NULL != usr->line) {
     
    212100                usr->line = (char *) NULL;
    213101        }
    214         tok_fini(&tok);
    215         free(tokens);
     102        if (NULL != tmp)
     103                free(tmp);
    216104
    217105        return rc;
    218 }
    219 
    220 void print_pipe_usage()
    221 {
    222         printf("Invalid syntax!\n");
    223         printf("Usage of redirection (pipes in the future):\n");
    224         printf("from filename | command ...\n");
    225         printf("from filename | command ... | to filename\n");
    226         printf("command ... | to filename\n");
    227        
    228 }
    229 
    230 int run_command(char **cmd, cliuser_t *usr, iostate_t *new_iostate)
    231 {
    232         int id = 0;
    233        
    234         /* We have rubbish */
    235         if (NULL == cmd[0]) {
    236                 return CL_ENOENT;
    237         }
    238        
    239         /* Is it a builtin command ? */
    240         if ((id = (is_builtin(cmd[0]))) > -1) {
    241                 return run_builtin(id, cmd, usr, new_iostate);
    242         }
    243        
    244         /* Is it a module ? */
    245         if ((id = (is_module(cmd[0]))) > -1) {
    246                 return run_module(id, cmd, new_iostate);
    247         }
    248 
    249         /* See what try_exec thinks of it */
    250         return try_exec(cmd[0], cmd, new_iostate);
    251106}
    252107
     
    255110        char *str;
    256111        int rc;
    257        
    258         tinput_set_prompt(tinput, usr->prompt);
     112
     113        fflush(stdout);
     114        console_set_style(fphone(stdout), STYLE_EMPHASIS);
     115        printf("%s", usr->prompt);
     116        fflush(stdout);
     117        console_set_style(fphone(stdout), STYLE_NORMAL);
    259118
    260119        rc = tinput_read(tinput, &str);
     
    289148        }
    290149
    291         tinput_set_compl_ops(tinput, &compl_ops);
    292 
    293150        return 0;
    294151}
Note: See TracChangeset for help on using the changeset viewer.