more cleaning
This commit is contained in:
183
sysexits/sysexits.c
Normal file
183
sysexits/sysexits.c
Normal file
@@ -0,0 +1,183 @@
|
||||
#include <ascii.h>
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include "usefulmacros.h"
|
||||
|
||||
/* Thanks to u/smcameron on Reddit. */
|
||||
|
||||
#define TAB_WIDTH 8
|
||||
|
||||
/* Changing ENUM to DEFINE will make this output the traditional BSD header
|
||||
* verbatim, without copyright notice. I don't have any fucking idea if that's
|
||||
* a copyright violation, but let's keep this as ENUM to skirt by that little
|
||||
* technicality.
|
||||
* I implemented sysexits(3) in the enum method before reading the BSD 4.0
|
||||
* source to see how they did it. */
|
||||
#define ENUM 1
|
||||
|
||||
static char *program_name = "sysexits";
|
||||
|
||||
//static const char comment_prefix[] = "/* ";
|
||||
static const char comment_prefix_ongoing[] = " * ";
|
||||
static const char comment_suffix[] = " */\n";
|
||||
|
||||
static const char header_prefix[] =
|
||||
"#ifndef _SYSEXITS_H\n"
|
||||
"#\tdefine _SYSEXITS_H\n"
|
||||
"enum{\n"
|
||||
;
|
||||
|
||||
/* ASSUMPTIONS:
|
||||
* - This array is always organized.
|
||||
* - All characters in descriptions are one space wide.
|
||||
* - The only whitespace in descriptions is ASCII_SP. */
|
||||
static const struct {
|
||||
char *desc;
|
||||
char *name;
|
||||
int status;
|
||||
}sysexits[] = {
|
||||
/* sysexit descriptions copied from FreeBSD's sysexits(3). */
|
||||
|
||||
{ "All is well.", /* except this one */
|
||||
"EX_OK", 0 },
|
||||
|
||||
{ "The command was used incorrectly, e.g., with the wrong number of"
|
||||
" arguments, a bad flag, a bad syntax in a parameter, or whatever.",
|
||||
"EX_USAGE", 64 },
|
||||
|
||||
{ "The input data was incorrect in some way. This should only be used"
|
||||
" for user's data and not system files.",
|
||||
"EX_DATAERR", 65 },
|
||||
|
||||
{ "An input file (not a system file) did not exist or was not readable."
|
||||
" This could also include errors like \"No message\" to a mailer (if it"
|
||||
" cared to catch it).",
|
||||
"EX_NOINPUT", 66 },
|
||||
|
||||
{ "The user specified did not exist. This might be used for mail"
|
||||
" addresses or remote logins.",
|
||||
"EX_NOUSER", 67 },
|
||||
|
||||
{ "The host specified did not exist. This is used in mail addresses or"
|
||||
" network requests.",
|
||||
"EX_NOHOST", 68 },
|
||||
|
||||
{ "A service is unavailable. This can occur if a support program or"
|
||||
" file does not exist. This can also be used as a catchall message"
|
||||
" when something you wanted to do does not work, but you do not know"
|
||||
" why.",
|
||||
"EX_UNAVAILABLE", 69 },
|
||||
|
||||
{ "An internal software error has been detected. This should be limited"
|
||||
" to non-operating system related errors as possible.",
|
||||
"EX_SOFTWARE", 70 },
|
||||
|
||||
{ "An operating system error has been detected. This is intended to be"
|
||||
" used for such things as \"cannot fork\", \"cannot create pipe\", or"
|
||||
" the like. It includes things like getuid returning a user that does"
|
||||
" not exist in the passwd file.",
|
||||
"EX_OSERR", 71 },
|
||||
|
||||
{ "Some system file (e.g., /etc/passwd, /var/run/utx.active, etc.) does"
|
||||
" not exist, cannot be opened, or has some sort of error (e.g., syntax"
|
||||
" error).",
|
||||
"EX_OSFILE", 72 },
|
||||
|
||||
{ "A (user specified) output file cannot be created.",
|
||||
"EX_CANTCREAT", 73 },
|
||||
|
||||
{ "An error occurred while doing I/O on some file.",
|
||||
"EX_IOERR", 74 },
|
||||
|
||||
{ "Temporary failure, indicating something that is not really an error."
|
||||
" In sendmail, this means that a mailer (e.g.) could not create a"
|
||||
" connection, and the request should be reattempted later.",
|
||||
"EX_TEMPFAIL", 75 },
|
||||
|
||||
{ "The remote system returned something that was \"not possible\" during a"
|
||||
" protocol exchange.",
|
||||
"EX_PROTOCOL", 76 },
|
||||
|
||||
{ "You did not have sufficient permission to perform the operation."
|
||||
" This is not intended for file system problems, which should use"
|
||||
" EX_NOINPUT or EX_CANTCREAT, but rather for higher level"
|
||||
" permissions.",
|
||||
"EX_NOPERM", 77 },
|
||||
|
||||
{ "Something was found in an unconfigured or misconfigured state.",
|
||||
"EX_CONFIG", 78 }
|
||||
};
|
||||
|
||||
static const char header_suffix[] =
|
||||
"};\n"
|
||||
"#endif /* ifndef _SYSEXITS_H */\n"
|
||||
;
|
||||
|
||||
static size_t i;
|
||||
|
||||
static int findbyint(int status){
|
||||
for(i = 0; i < ARRAYLEN(sysexits); ++i)
|
||||
if(sysexits[i].status == status)
|
||||
return i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
static void output_comment(int fd, int indentation, int width, char *comment){
|
||||
size_t word_start;
|
||||
size_t line_start;
|
||||
|
||||
for(i = 0, line_start = 0, word_start = 0; ; ++i)
|
||||
switch(comment[i]){
|
||||
case '\0':
|
||||
while( i - line_start
|
||||
+ ARRAYLEN(comment_suffix)
|
||||
+ indentation * TAB_WIDTH
|
||||
> width){
|
||||
i = word_start - 2; /* - current char, - space */
|
||||
write(
|
||||
fd, comment_prefix_ongoing,
|
||||
ARRAYLEN(comment_prefix_ongoing)
|
||||
);
|
||||
write(fd, comment + line_start, i - line_start);
|
||||
i += 2; /* + space, + next word char */
|
||||
write(fd, "\n", 1);
|
||||
}
|
||||
write(fd, comment + line_start, i - line_start);
|
||||
write(fd, comment_suffix, ARRAYLEN(comment_suffix));
|
||||
break;
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
static void output_header(void){
|
||||
write(1, header_prefix, ARRAYLEN(header_prefix) - 1);
|
||||
for(i = 0; i < ARRAYLEN(sysexits); ++i){
|
||||
//output_comment(1, 1 * TAB_WIDTH, 80, sysexits[i].desc);
|
||||
#ifdef ENUM
|
||||
fprintf(stdout, "\t%s = %d%s",
|
||||
sysexits[i].name,
|
||||
sysexits[i].status,
|
||||
i < ARRAYLEN(sysexits) - 1 ? ",\n" : "\n"
|
||||
);
|
||||
#endif /* ifdef ENUM */
|
||||
#ifdef DEFINE
|
||||
fprintf(stdout, "#\tdefine %s %d\n",
|
||||
sysexits[i].name,
|
||||
sysexits[i].status
|
||||
);
|
||||
#endif /* ifdef DEFINE */
|
||||
}
|
||||
fflush(stdout); /* Fixes actual issue. */
|
||||
write(1, header_suffix, ARRAYLEN(header_suffix) - 1);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[]){
|
||||
if(argv[0] == NULL){
|
||||
argv[0] = program_name;
|
||||
++argc;
|
||||
}
|
||||
|
||||
output_header();
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user