Changeset 3be62bc in mainline for uspace/srv/net/app/ping/ping.c


Ignore:
Timestamp:
2010-03-09T22:23:18Z (14 years ago)
Author:
Lukas Mejdrech <lukasmejdrech@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
9f2ea28
Parents:
a8a13d0
Message:
  • net app command line argument checks, * code reorganization
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/srv/net/app/ping/ping.c

    ra8a13d0 r3be62bc  
    3939#include <task.h>
    4040#include <time.h>
     41#include <ipc/ipc.h>
    4142#include <ipc/services.h>
    4243
     
    6768/** Prints the application help.
    6869 */
    69 void print_help(void);
    70 
    71 /** Translates the character string to the address family number.
    72  *  @param[in] name The address family name.
    73  *  @returns The corresponding address family number.
    74  *  @returns EAFNOSUPPORTED if the address family is not supported.
    75  */
    76 int parse_address_family(const char * name);
    77 
    78 void print_help(void){
    79         printf(
    80                 "Network Ping aplication\n" \
    81                 "Usage: ping [options] numeric_address\n" \
    82                 "Where options are:\n" \
    83                 "\n" \
    84                 "-c request_count | --count=request_count\n" \
    85                 "\tThe number of packets the application sends. The default is three (3).\n" \
    86                 "\n" \
    87                 "--dont_fragment\n" \
    88                 "\tDisable packet fragmentation.\n"
    89                 "\n" \
    90                 "-f address_family | --family=address_family\n" \
    91                 "\tThe given address family. Only the AF_INET and AF_INET6 are supported.\n"
    92                 "\n" \
    93                 "-h | --help\n" \
    94                 "\tShow this application help.\n"
    95                 "\n" \
    96                 "-s packet_size | --size=packet_size\n" \
    97                 "\tThe packet data size the application sends. The default is 38 bytes.\n" \
    98                 "\n" \
    99                 "-t timeout | --timeout=timeout\n" \
    100                 "\tThe number of miliseconds the application waits for a reply. The default is three thousands (3 000).\n" \
    101                 "\n" \
    102                 "--tos=tos\n" \
    103                 "\tThe type of service to be used.\n" \
    104                 "\n" \
    105                 "--ttl=ttl\n" \
    106                 "\tThe time to live to be used.\n" \
    107                 "\n" \
    108                 "-v | --verbose\n" \
    109                 "\tShow all output messages.\n"
    110         );
    111 }
    112 
    113 int parse_address_family(const char * name){
    114         if(str_lcmp(name, "AF_INET", 7) == 0){
    115                 return AF_INET;
    116         }else if(str_lcmp(name, "AF_INET6", 8) == 0){
    117                 return AF_INET6;
    118         }
    119         return EAFNOSUPPORT;
    120 }
     70void ping_print_help(void);
    12171
    12272int main(int argc, char * argv[]){
     
    12676        int verbose                     = 0;
    12777        int dont_fragment       = 0;
    128         ip_ttl_t ttl                            = 0;
    129         ip_tos_t tos                            = 0;
     78        ip_ttl_t ttl            = 0;
     79        ip_tos_t tos            = 0;
    13080        int count                       = 3;
    131         suseconds_t timeout                     = 3000;
     81        suseconds_t timeout     = 3000;
    13282        int family                      = AF_INET;
    13383
    134         socklen_t max_length            = sizeof(struct sockaddr_in6);
     84        socklen_t max_length                            = sizeof(struct sockaddr_in6);
    13585        uint8_t address_data[max_length];
    136         struct sockaddr * address               = (struct sockaddr *) address_data;
     86        struct sockaddr * address                       = (struct sockaddr *) address_data;
    13787        struct sockaddr_in * address_in         = (struct sockaddr_in *) address;
    13888        struct sockaddr_in6 * address_in6       = (struct sockaddr_in6 *) address;
     
    14797        int index;
    14898
     99        // print the program label
    149100        printf("Task %d - ", task_get_id());
    150101        printf("%s\n", NAME);
    151102
    152         if(argc <= 1){
    153                 print_help();
    154                 return EINVAL;
    155         }
    156 
    157         for(index = 1; (index < argc - 1) || ((index == argc) && (argv[index][0] == '-')); ++ index){
     103        // parse the command line arguments
     104        // stop before the last argument if it does not start with the minus sign ('-')
     105        for(index = 1; (index < argc - 1) || ((index == argc - 1) && (argv[index][0] == '-')); ++ index){
     106                // options should start with the minus sign ('-')
    158107                if(argv[index][0] == '-'){
    159108                        switch(argv[index][1]){
     109                                // short options with only one letter
    160110                                case 'c':
    161111                                        ERROR_PROPAGATE(parse_parameter_int(argc, argv, &index, &count, "count", 0));
     
    165115                                        break;
    166116                                case 'h':
    167                                         print_help();
     117                                        ping_print_help();
    168118                                        return EOK;
    169119                                        break;
     
    179129                                        verbose = 1;
    180130                                        break;
     131                                // long options with the double minus sign ('-')
    181132                                case '-':
    182133                                        if(str_lcmp(argv[index] + 2, "count=", 6) == 0){
     
    187138                                                ERROR_PROPAGATE(parse_parameter_name_int(argc, argv, &index, &family, "address family", 9, parse_address_family));
    188139                                        }else if(str_lcmp(argv[index] + 2, "help", 5) == 0){
    189                                                 print_help();
     140                                                ping_print_help();
    190141                                                return EOK;
    191142                                        }else if(str_lcmp(argv[index] + 2, "size=", 5) == 0){
     
    205156                                        }else{
    206157                                                print_unrecognized(index, argv[index] + 2);
    207                                                 print_help();
     158                                                ping_print_help();
    208159                                                return EINVAL;
    209160                                        }
     
    211162                                default:
    212163                                        print_unrecognized(index, argv[index] + 1);
    213                                         print_help();
     164                                        ping_print_help();
    214165                                        return EINVAL;
    215166                        }
    216167                }else{
    217168                        print_unrecognized(index, argv[index]);
    218                         print_help();
     169                        ping_print_help();
    219170                        return EINVAL;
    220171                }
    221172        }
    222173
     174        // if not before the last argument containing the address
     175        if(index >= argc){
     176                printf("Command line error: missing address\n");
     177                ping_print_help();
     178                return EINVAL;
     179        }
     180
     181        // prepare the address buffer
    223182        bzero(address_data, max_length);
    224183        switch(family){
     
    238197        }
    239198
     199        // parse the last argument which should contain the address
    240200        if(ERROR_OCCURRED(inet_pton(family, argv[argc - 1], address_start))){
    241201                fprintf(stderr, "Address parse error %d\n", ERROR_CODE);
     
    243203        }
    244204
     205        // connect to the ICMP module
    245206        icmp_phone = icmp_connect_module(SERVICE_ICMP, ICMP_CONNECT_TIMEOUT);
    246207        if(icmp_phone < 0){
     
    249210        }
    250211
     212        // print the ping header
    251213        printf("PING %d bytes of data\n", size);
    252214        if(ERROR_OCCURRED(inet_ntop(address->sa_family, address_start, address_string, sizeof(address_string)))){
     
    256218        }
    257219
     220        // do count times
    258221        while(count > 0){
     222
     223                // get the starting time
    259224                if(ERROR_OCCURRED(gettimeofday(&time_before, NULL))){
    260225                        fprintf(stderr, "Get time of day error %d\n", ERROR_CODE);
     226                        // release the ICMP phone
     227                        ipc_hangup(icmp_phone);
    261228                        return ERROR_CODE;
    262229                }
     230
     231                // request the ping
    263232                result = icmp_echo_msg(icmp_phone, size, timeout, ttl, tos, dont_fragment, address, addrlen);
     233
     234                // get the ending time
    264235                if(ERROR_OCCURRED(gettimeofday(&time_after, NULL))){
    265236                        fprintf(stderr, "Get time of day error %d\n", ERROR_CODE);
     237                        // release the ICMP phone
     238                        ipc_hangup(icmp_phone);
    266239                        return ERROR_CODE;
    267240                }
     241
     242                // print the result
    268243                switch(result){
    269244                        case ICMP_ECHO:
     
    283258        }
    284259
     260        // release the ICMP phone
     261        ipc_hangup(icmp_phone);
     262
    285263        return EOK;
    286264}
    287265
     266void ping_print_help(void){
     267        printf(
     268                "Network Ping aplication\n" \
     269                "Usage: ping [options] numeric_address\n" \
     270                "Where options are:\n" \
     271                "\n" \
     272                "-c request_count | --count=request_count\n" \
     273                "\tThe number of packets the application sends. The default is three (3).\n" \
     274                "\n" \
     275                "--dont_fragment\n" \
     276                "\tDisable packet fragmentation.\n"
     277                "\n" \
     278                "-f address_family | --family=address_family\n" \
     279                "\tThe given address family. Only the AF_INET and AF_INET6 are supported.\n"
     280                "\n" \
     281                "-h | --help\n" \
     282                "\tShow this application help.\n"
     283                "\n" \
     284                "-s packet_size | --size=packet_size\n" \
     285                "\tThe packet data size the application sends. The default is 38 bytes.\n" \
     286                "\n" \
     287                "-t timeout | --timeout=timeout\n" \
     288                "\tThe number of miliseconds the application waits for a reply. The default is three thousands (3 000).\n" \
     289                "\n" \
     290                "--tos=tos\n" \
     291                "\tThe type of service to be used.\n" \
     292                "\n" \
     293                "--ttl=ttl\n" \
     294                "\tThe time to live to be used.\n" \
     295                "\n" \
     296                "-v | --verbose\n" \
     297                "\tShow all output messages.\n"
     298        );
     299}
     300
    288301/** @}
    289302 */
Note: See TracChangeset for help on using the changeset viewer.