cmdline.c 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <string.h>
  4. #include "cmdline.h"
  5. #define MAX_LENGTH_PER_PARAMETER_FORMAT 128
  6. #define MAX_PARAMETERS_PER_OPTION 8
  7. static int parse_option_parameters(const char **params, const char *format, void *storage)
  8. {
  9. int error = 0;
  10. int fmt_pos=0;
  11. int pa_num=0;
  12. //fprintf (stderr, "parse_option_parameters !\n");
  13. while (1) {
  14. char s[MAX_LENGTH_PER_PARAMETER_FORMAT];
  15. int s_pos=0;
  16. while (format[fmt_pos] == ' ') fmt_pos++;
  17. while ((format[fmt_pos] != ' ') &&
  18. (format[fmt_pos] != 0))
  19. s[s_pos++] = format[fmt_pos++];
  20. if (s_pos==0) break; /* end of format string */
  21. s[s_pos++] = 0;
  22. if (params[pa_num]==NULL) {error++;break;}
  23. //fprintf (stderr, "option parameter tag %s value %s\n", s, params[pa_num]);
  24. if (storage!=NULL) sscanf(params[pa_num], s, &(((int*)storage)[pa_num]));
  25. pa_num++;
  26. }
  27. if (error!=0) return -error;
  28. return pa_num;
  29. }
  30. /* return 1 if help mode was active
  31. return negative number if an error occured
  32. return 0 if everything went fine */
  33. int parse_arguments(int argc, const char **argv, const struct CmdLineOption *options, char **moreParameters, const char *helpText)
  34. {
  35. int error = 0, helpmode = 0;
  36. int opt, arg;
  37. int numMoreParameters = 0;
  38. if (options==NULL) return -1;
  39. for (opt=0; options[opt].name != NULL; opt++) {
  40. if (options[opt].storage != NULL) {
  41. if (options[opt].parameters==NULL) *(int*)options[opt].storage = 0;
  42. else if (options[opt].default_value != NULL) {
  43. const char *defaults = options[opt].default_value;
  44. const char *default_argv[MAX_PARAMETERS_PER_OPTION];
  45. int arg = 0, pos = 0;
  46. while (1) {
  47. int len = 0;
  48. while (defaults[pos] == ' ') pos++;
  49. default_argv[arg] = &(defaults[pos]);
  50. while ((defaults[pos] != ' ')&&
  51. (defaults[pos] != 0)) {pos++;len++;}
  52. if (len==0) {
  53. default_argv[arg] = NULL;
  54. break;
  55. }
  56. arg++;
  57. }
  58. parse_option_parameters(default_argv, options[opt].parameters, options[opt].storage);
  59. }
  60. }
  61. }
  62. for (arg=1; arg<argc; arg++) {
  63. const struct CmdLineOption *foundOption = NULL;
  64. int minuses = 0;
  65. while ((argv[arg][minuses]=='-')&&(minuses<2)) minuses++;
  66. if (minuses > 0) {
  67. if ((!strcmp("help", &(argv[arg][minuses])))||
  68. (!strcmp("h", &argv[arg][minuses]))) {
  69. helpmode = 1;
  70. break;
  71. }
  72. for (opt=0; options[opt].name != NULL; opt++) {
  73. if (!strcmp(options[opt].name, &(argv[arg][minuses]))) {
  74. foundOption = &(options[opt]);
  75. break;
  76. }
  77. }
  78. }
  79. if (foundOption!=NULL) {
  80. //fprintf(stderr, "option %s was recognized\n", (argv[arg]));
  81. if (foundOption->parameters!=NULL) {
  82. int ret = parse_option_parameters(&(argv[arg+1]), foundOption->parameters, foundOption->storage);
  83. if (ret<0) { fprintf (stderr, "cmdline: error reading this option!\n"); error++; break; }
  84. arg+=ret;
  85. } else { /* there are no parameters */
  86. if (foundOption->storage!=NULL) *(int*)(foundOption->storage) = 1;
  87. }
  88. } else { /* option not recognized */
  89. if (moreParameters) {
  90. moreParameters[numMoreParameters++] = (char*)argv[arg];
  91. }
  92. /* else fprintf(stderr, "option %s not recognized\n", (argv[arg]));*/
  93. }
  94. }
  95. moreParameters[numMoreParameters] = NULL;
  96. if (helpmode)
  97. return print_help ( options, helpText );
  98. return -error;
  99. }
  100. int print_help ( const struct CmdLineOption *options, const char *helpText )
  101. {
  102. if(helpText!=NULL) fprintf(stdout, "%s\n",helpText);
  103. fprintf(stdout, "Options:\n");
  104. int opt;
  105. for (opt=0; options[opt].name != NULL; opt++) {
  106. if (options[opt].description!=NULL) {
  107. fprintf(stdout, " -%-20s%s", options[opt].name, options[opt].description);
  108. if (options[opt].default_value!=NULL)
  109. fprintf(stdout, " (dflt: %s)",options[opt].default_value);
  110. fprintf(stdout, "\n");
  111. }
  112. }
  113. return 1;
  114. }