summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorBruce Guenter <bruce@untroubled.org>2012-04-23 10:59:54 -0600
committerBruce Guenter <bruce@untroubled.org>2012-04-23 10:59:54 -0600
commitfb6326ff2e5eb767e53f7f1e30748bcf489d26df (patch)
tree3f15727c166c83fa7e0037210b6bb29432f79821 /lib
parentd0cc4538313204a434982a42aa1182fca5c032e2 (diff)
parent75f4a52ba1fa1916a5c64cf279ef883ecb24c142 (diff)
Merge branch 'lsb'
Conflicts: NEWS src/sendmail.cc
Diffstat (limited to 'lib')
-rw-r--r--lib/cli++/Makefile.am2
-rw-r--r--lib/cli++/cli++.h7
-rw-r--r--lib/cli++/main.cc112
-rw-r--r--lib/cli++/only_long.cc3
-rw-r--r--lib/mystring/upper.cc4
5 files changed, 79 insertions, 49 deletions
diff --git a/lib/cli++/Makefile.am b/lib/cli++/Makefile.am
index b409e4c..c4fdd52 100644
--- a/lib/cli++/Makefile.am
+++ b/lib/cli++/Makefile.am
@@ -4,6 +4,6 @@ EXTRA_DIST = clitest.cc cli++topod.pl
INCLUDES = -I..
#LIBS = @LIBS@ -L. -lcli++ -L../lib -lvmailmgr
-libcli___a_SOURCES = cli++.h main.cc messages.cc
+libcli___a_SOURCES = cli++.h main.cc messages.cc only_long.cc
#clitest_SOURCES = clitest.cc
diff --git a/lib/cli++/cli++.h b/lib/cli++/cli++.h
index 413815b..f765ba8 100644
--- a/lib/cli++/cli++.h
+++ b/lib/cli++/cli++.h
@@ -25,10 +25,12 @@ struct cli_option
const char* defaultstr;
int set(const char* arg);
- int parse_long_eq(const char* arg);
- int parse_long_noeq(const char* arg);
+ int parse_long_eq(const char* arg, int as_short);
+ int parse_long_noeq(const char* arg, int as_short);
};
+#define CLI_OPTION_END {0, 0, cli_option::flag, 0, 0, 0, 0}
+
/* The following are required from the CLI program */
extern const char* cli_program;
extern const char* cli_help_prefix;
@@ -37,6 +39,7 @@ extern const char* cli_args_usage;
extern const int cli_args_min;
extern const int cli_args_max;
extern cli_option cli_options[];
+extern const bool cli_only_long;
extern int cli_main(int argc, char* argv[]);
/* The following are provided to the CLI program */
diff --git a/lib/cli++/main.cc b/lib/cli++/main.cc
index 58d9221..f0eb014 100644
--- a/lib/cli++/main.cc
+++ b/lib/cli++/main.cc
@@ -49,14 +49,14 @@ static void build_options()
options[optionc-1] = &help_option;
}
-static inline unsigned max(unsigned a, unsigned b)
+static inline int max(int a, int b)
{
return (a>b) ? a : b;
}
-static const char* fill(unsigned i)
+static const char* fill(int i)
{
- static unsigned lastlen = 0;
+ static int lastlen = 0;
static char* buf = 0;
if(i > lastlen) {
delete[] buf;
@@ -73,39 +73,43 @@ static void show_usage()
fout << "usage: " << cli_program << " [flags] " << cli_args_usage << endl;
}
-static unsigned calc_max_width()
+int calc_width(const cli_option* o)
{
- // maxwidth is the maximum width of the long argument
- unsigned maxwidth = 0;
- for(unsigned i = 0; i < optionc; i++) {
- unsigned width = 0;
- cli_option* o = options[i];
- if(o->name) {
- width += strlen(o->name);
- switch(o->type) {
- case cli_option::string: width += 6; break;
- case cli_option::integer: width += 4; break;
- case cli_option::uinteger: width += 4; break;
- case cli_option::stringlist: width += 5; break;
- case cli_option::flag: break;
- case cli_option::counter: break;
- }
+ int width = (o->ch || !cli_only_long) ? 4 : 2;
+ if (o->name) {
+ width += strlen(o->name) + 2 + !cli_only_long;
+ switch (o->type) {
+ case cli_option::string: width += 6; break;
+ case cli_option::integer: width += 4; break;
+ case cli_option::uinteger: width += 4; break;
+ case cli_option::stringlist: width += 5; break;
+ case cli_option::flag: break;
+ case cli_option::counter: break;
}
- if(width > maxwidth)
- maxwidth = width;
}
+ return width;
+}
+
+static int calc_max_width()
+{
+ // maxwidth is the maximum width of the option text prefix
+ int maxwidth = 0;
+ for(unsigned i = 0; i < optionc; i++)
+ maxwidth = max(maxwidth, calc_width(options[i]));
return maxwidth;
}
-static void show_option(cli_option* o, unsigned maxwidth)
+static void show_option(const cli_option* o, int maxwidth)
{
if(o == &help_option)
fout << '\n';
+ fout << " ";
if(o->ch)
- fout << " -" << o->ch;
- else
- fout << " ";
- fout << (o->ch && o->name ? ", " : " ");
+ fout << '-' << o->ch;
+ else if (!cli_only_long)
+ fout << " ";
+ if (o->ch || !cli_only_long)
+ fout << (o->ch && o->name ? ", " : " ");
if(o->name) {
const char* extra = "";
switch(o->type) {
@@ -116,21 +120,22 @@ static void show_option(cli_option* o, unsigned maxwidth)
case cli_option::flag: break;
case cli_option::counter: break;
}
- fout << "--" << o->name << extra
- << fill(maxwidth - strlen(o->name) - strlen(extra) + 2);
+ fout << (cli_only_long ? "-" : "--") << o->name << extra
+ << fill(maxwidth - strlen(o->name) - strlen(extra) - !cli_only_long
+ - (o->ch || !cli_only_long ? 4 : 0));
}
else
- fout << fill(maxwidth+4);
+ fout << fill(maxwidth-3);
fout << o->helpstr << '\n';
if(o->defaultstr)
- fout << fill(maxwidth+10) << "(Defaults to " << o->defaultstr << ")\n";
+ fout << fill(maxwidth+3) << "(Defaults to " << o->defaultstr << ")\n";
}
static void show_help()
{
if(cli_help_prefix)
fout << cli_help_prefix;
- unsigned maxwidth = calc_max_width();
+ int maxwidth = calc_max_width();
for(unsigned i = 0; i < optionc; i++)
show_option(options[i], maxwidth);
if(cli_help_suffix)
@@ -230,46 +235,65 @@ static int parse_short(int argc, char* argv[])
return 0;
}
-int cli_option::parse_long_eq(const char* arg)
+static void option_error(const cli_option* o, int as_short, const char* text)
+{
+ ferr << argv0 << ": option ";
+ if (as_short)
+ ferr << '-' << o->ch;
+ else
+ ferr << (cli_only_long ? "-" : "--") << o->name;
+ ferr << text << endl;
+}
+
+int cli_option::parse_long_eq(const char* arg, int as_short)
{
if(type == flag || type == counter) {
- ferr << argv0 << ": option --" << name
- << " does not take a value." << endl;
+ option_error(this, as_short, " does not take a value.");
return -1;
}
else
return set(arg)-1;
}
-int cli_option::parse_long_noeq(const char* arg)
+int cli_option::parse_long_noeq(const char* arg, int as_short)
{
if(type == flag || type == counter)
return set(0);
else if(arg)
return set(arg);
else {
- ferr << argv0 << ": option --" << name
- << " requires a value." << endl;
+ option_error(this, as_short, " requires a value.");
return -1;
}
}
static int parse_long(int, char* argv[])
{
- const char* arg = argv[0]+2;
+ const char* arg = argv[0]+1;
+ // Handle both short and long args
+ if (arg[0] == '-')
+ ++arg;
for(unsigned j = 0; j < optionc; j++) {
cli_option* o = options[j];
+ if (cli_only_long && o->ch) {
+ if (arg[0] == o->ch) {
+ if (arg[1] == '\0')
+ return o->parse_long_noeq(argv[1], true);
+ else if (arg[1] == '=')
+ return o->parse_long_eq(arg+2, true);
+ }
+ }
if(o->name) {
size_t len = strlen(o->name);
if(!memcmp(arg, o->name, len)) {
if(arg[len] == '\0')
- return o->parse_long_noeq(argv[1]);
+ return o->parse_long_noeq(argv[1], false);
else if(arg[len] == '=')
- return o->parse_long_eq(arg+len+1);
+ return o->parse_long_eq(arg+len+1, false);
}
}
}
- ferr << argv0 << ": unknown option string: '--" << arg << "'" << endl;
+ ferr << argv0 << ": unknown option string: '" << argv[0] << "'" << endl;
return -1;
}
@@ -288,9 +312,9 @@ static int parse_args(int argc, char* argv[])
i++;
break;
}
- int j = (arg[1] != '-') ?
- parse_short(argc-i, argv+i) :
- parse_long(argc-i, argv+i);
+ int j = (!cli_only_long && arg[1] != '-')
+ ? parse_short(argc-i, argv+i)
+ : parse_long(argc-i, argv+i);
if(j < 0)
usage(1);
else
diff --git a/lib/cli++/only_long.cc b/lib/cli++/only_long.cc
new file mode 100644
index 0000000..3800a25
--- /dev/null
+++ b/lib/cli++/only_long.cc
@@ -0,0 +1,3 @@
+#include "cli++.h"
+
+const bool cli_only_long = false;
diff --git a/lib/mystring/upper.cc b/lib/mystring/upper.cc
index 0e7ca5b..5015770 100644
--- a/lib/mystring/upper.cc
+++ b/lib/mystring/upper.cc
@@ -8,8 +8,8 @@ mystring mystring::upper() const
const char* in = rep->buf + length;
bool changed = false;
for(char* out = buf+length; out >= buf; in--, out--)
- if(isupper(*in)) {
- *out = tolower(*in);
+ if(islower(*in)) {
+ *out = toupper(*in);
changed = true;
}
else