str(1): edit out goto
This commit is contained in:
parent
71f4a411b6
commit
c8b4f7a8b3
54
src/str.c
54
src/str.c
@ -20,11 +20,11 @@
|
|||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <stddef.h> /* NULL */
|
#include <stddef.h> /* NULL */
|
||||||
#include <stdio.h> /* fprintf(3) */
|
#include <stdio.h> /* fprintf(3) */
|
||||||
#include <stdlib.h> /* EXIT_FAILURE */
|
#include <stdlib.h> /* size_t, EXIT_FAILURE */
|
||||||
#include <string.h> /* strcmp(3) */
|
#include <string.h> /* strcmp(3) */
|
||||||
#include <sysexits.h>
|
#include <sysexits.h> /* EX_USAGE */
|
||||||
|
|
||||||
static char *program_name = "str";
|
char *program_name = "str";
|
||||||
|
|
||||||
static struct {
|
static struct {
|
||||||
char *name;
|
char *name;
|
||||||
@ -41,41 +41,41 @@ static struct {
|
|||||||
{ "isprint", isprint },
|
{ "isprint", isprint },
|
||||||
{ "ispunct", ispunct },
|
{ "ispunct", ispunct },
|
||||||
{ "isspace", isspace },
|
{ "isspace", isspace },
|
||||||
{ "isupper", isupper }
|
{ "isupper", isupper },
|
||||||
|
{ NULL, NULL } /* marks end */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
int usage(char *s){
|
||||||
|
fprintf(stderr, "Usage: %s type string...\n", s);
|
||||||
|
return EX_USAGE;
|
||||||
|
}
|
||||||
|
|
||||||
int main(int argc, char *argv[]){
|
int main(int argc, char *argv[]){
|
||||||
int ctype;
|
size_t ctype; /* selected from ctypes.h; index of ctype */
|
||||||
int i;
|
int retval;
|
||||||
int r;
|
|
||||||
|
|
||||||
if (argc >= 3) {
|
if (argc < 3) { return usage(argv[0] == NULL ? program_name : argv[0]); }
|
||||||
for (ctype = 0; ctype < (sizeof ctypes) / (sizeof *ctypes); ++ctype) {
|
|
||||||
if(strcmp(argv[1], ctypes[ctype].name) == 0) {
|
|
||||||
goto pass;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fprintf(
|
for ( /* iterate ctypes */
|
||||||
stderr,
|
ctype = 0;
|
||||||
"Usage: %s type string...\n",
|
ctypes[ctype].f != NULL /* break at the end of ctypes */
|
||||||
argv[0] == NULL ? program_name : argv[0]
|
&& strcmp(argv[1], ctypes[ctype].name) != 0; /* break at match */
|
||||||
|
++ctype
|
||||||
);
|
);
|
||||||
|
|
||||||
return EX_USAGE;
|
if (ctypes[ctype].f == NULL) { return usage(argv[0]); }
|
||||||
|
|
||||||
pass: for (argv += 2, r = 1; *argv != NULL; ++argv) {
|
/* iterate args */
|
||||||
for (i = 0; argv[0][i] != '\0'; ++i) {
|
for (argv += 2, retval = EXIT_FAILURE; *argv != NULL; ++argv) {
|
||||||
/* First checks if argv[0][i] is valid ASCII; ctypes(3)
|
for (size_t i = 0; argv[0][i] != '\0'; ++i) { /* iterate arg bytes */
|
||||||
* don't handle non-ASCII.
|
/* First checks if argv[0][i] is valid ASCII; ctypes(3) don't
|
||||||
* This is bad. */
|
* handle non-ASCII. This is bad. */
|
||||||
if(
|
if(
|
||||||
(unsigned char)argv[0][i] < 0x80 && !ctypes[ctype].f(argv[0][i])
|
(unsigned char)argv[0][i] < 0x80 && !ctypes[ctype].f(argv[0][i])
|
||||||
) { return 1; }
|
) { return EXIT_FAILURE; }
|
||||||
else { r = 0; }
|
else { retval = EXIT_SUCCESS; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return r;
|
return retval;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user