zf

zenflows testing
git clone https://s.sonu.ch/~srfsh/zf.git
Log | Files | Refs | Submodules | README | LICENSE

cli.c (5070B)


      1 #include <getopt.h>
      2 #include "cli.h"
      3 
      4 const char* cli_info_purpose = "A flexible command-line interface for the FSEvents API";
      5 const char* cli_info_usage = "Usage: fsevent_watch [OPTIONS]... [PATHS]...";
      6 const char* cli_info_help[] = {
      7   "  -h, --help                you're looking at it",
      8   "  -V, --version             print version number and exit",
      9   "  -p, --show-plist          display the embedded Info.plist values",
     10   "  -s, --since-when=EventID  fire historical events since ID",
     11   "  -l, --latency=seconds     latency period (default='0.5')",
     12   "  -n, --no-defer            enable no-defer latency modifier",
     13   "  -r, --watch-root          watch for when the root path has changed",
     14   // "  -i, --ignore-self         ignore current process",
     15   "  -F, --file-events         provide file level event data",
     16   "  -f, --format=name         output format (ignored)",
     17   0
     18 };
     19 
     20 static void default_args (struct cli_info* args_info)
     21 {
     22   args_info->since_when_arg     = kFSEventStreamEventIdSinceNow;
     23   args_info->latency_arg        = 0.5;
     24   args_info->no_defer_flag      = false;
     25   args_info->watch_root_flag    = false;
     26   args_info->ignore_self_flag   = false;
     27   args_info->file_events_flag   = false;
     28   args_info->mark_self_flag     = false;
     29   args_info->format_arg         = 0;
     30 }
     31 
     32 static void cli_parser_release (struct cli_info* args_info)
     33 {
     34   unsigned int i;
     35 
     36   for (i=0; i < args_info->inputs_num; ++i) {
     37     free(args_info->inputs[i]);
     38   }
     39 
     40   if (args_info->inputs_num) {
     41     free(args_info->inputs);
     42   }
     43 
     44   args_info->inputs_num = 0;
     45 }
     46 
     47 void cli_parser_init (struct cli_info* args_info)
     48 {
     49   default_args(args_info);
     50 
     51   args_info->inputs = 0;
     52   args_info->inputs_num = 0;
     53 }
     54 
     55 void cli_parser_free (struct cli_info* args_info)
     56 {
     57   cli_parser_release(args_info);
     58 }
     59 
     60 static void cli_print_info_dict (const void *key,
     61                                  const void *value,
     62                                  void *context)
     63 {
     64   CFStringRef entry = CFStringCreateWithFormat(NULL, NULL,
     65     CFSTR("%@:\n  %@"), key, value);
     66   if (entry) {
     67     CFShow(entry);
     68     CFRelease(entry);
     69   }
     70 }
     71 
     72 void cli_show_plist (void)
     73 {
     74   CFBundleRef mainBundle = CFBundleGetMainBundle();
     75   CFRetain(mainBundle);
     76   CFDictionaryRef mainBundleDict = CFBundleGetInfoDictionary(mainBundle);
     77   if (mainBundleDict) {
     78     CFRetain(mainBundleDict);
     79     printf("Embedded Info.plist metadata:\n\n");
     80     CFDictionaryApplyFunction(mainBundleDict, cli_print_info_dict, NULL);
     81     CFRelease(mainBundleDict);
     82   }
     83   CFRelease(mainBundle);
     84   printf("\n");
     85 }
     86 
     87 void cli_print_version (void)
     88 {
     89   printf("%s %s\n\n", "VXZ", "1.0");
     90 }
     91 
     92 void cli_print_help (void)
     93 {
     94   cli_print_version();
     95 
     96   printf("\n%s\n", cli_info_purpose);
     97   printf("\n%s\n", cli_info_usage);
     98   printf("\n");
     99 
    100   int i = 0;
    101   while (cli_info_help[i]) {
    102     printf("%s\n", cli_info_help[i++]);
    103   }
    104 }
    105 
    106 int cli_parser (int argc, const char** argv, struct cli_info* args_info)
    107 {
    108   static struct option longopts[] = {
    109     { "help",         no_argument,        NULL, 'h' },
    110     { "version",      no_argument,        NULL, 'V' },
    111     { "show-plist",   no_argument,        NULL, 'p' },
    112     { "since-when",   required_argument,  NULL, 's' },
    113     { "latency",      required_argument,  NULL, 'l' },
    114     { "no-defer",     no_argument,        NULL, 'n' },
    115     { "watch-root",   no_argument,        NULL, 'r' },
    116     { "ignore-self",  no_argument,        NULL, 'i' },
    117     { "file-events",  no_argument,        NULL, 'F' },
    118     { "mark-self",    no_argument,        NULL, 'm' },
    119     { "format",       required_argument,  NULL, 'f' },
    120     { 0, 0, 0, 0 }
    121   };
    122 
    123   const char* shortopts = "hVps:l:nriFf:";
    124 
    125   int c = -1;
    126 
    127   while ((c = getopt_long(argc, (char * const*)argv, shortopts, longopts, NULL)) != -1) {
    128     switch(c) {
    129     case 's': // since-when
    130       args_info->since_when_arg = strtoull(optarg, NULL, 0);
    131       break;
    132     case 'l': // latency
    133       args_info->latency_arg = strtod(optarg, NULL);
    134       break;
    135     case 'n': // no-defer
    136       args_info->no_defer_flag = true;
    137       break;
    138     case 'r': // watch-root
    139       args_info->watch_root_flag = true;
    140       break;
    141     case 'i': // ignore-self
    142       args_info->ignore_self_flag = true;
    143       break;
    144     case 'F': // file-events
    145       args_info->file_events_flag = true;
    146       break;
    147     case 'm': // mark-self
    148       args_info->mark_self_flag = true;
    149       break;
    150     case 'f': // format
    151       // XXX: ignored
    152       break;
    153     case 'V': // version
    154       cli_print_version();
    155       exit(EXIT_SUCCESS);
    156     case 'p': // show-plist
    157       cli_show_plist();
    158       exit(EXIT_SUCCESS);
    159     case 'h': // help
    160     case '?': // invalid option
    161     case ':': // missing argument
    162       cli_print_help();
    163       exit((c == 'h') ? EXIT_SUCCESS : EXIT_FAILURE);
    164     }
    165   }
    166 
    167   if (optind < argc) {
    168     int i = 0;
    169     args_info->inputs_num = (unsigned int)(argc - optind);
    170     args_info->inputs =
    171       (char**)(malloc ((args_info->inputs_num)*sizeof(char*)));
    172     while (optind < argc)
    173       if (argv[optind++] != argv[0]) {
    174         args_info->inputs[i++] = strdup(argv[optind-1]);
    175       }
    176   }
    177 
    178   return EXIT_SUCCESS;
    179 }
    180