/*+JMJ
* cmd.c - tir HTML renderer command line interface
* Copyright 2011 David Meyer <
[email protected]>
* cmd.c is part of tirrender
*
* 2011-07-28
* cmd.c implements a command line interface for the tirrender
* HTML rendering engine (implemented in common.c). The command
* line interface is intended for testing rendering functionality
* and for static rendering (rendered output saved to .html file
* for later and repeated access). cgi.c will implement CGI
* interface for dynamic rendering (rendered output generated for
* each HTTP request and returned to browser).
*/
#include <stdio.h>
#include <string.h>
#include "krcompat.h"
#include "tirrender.h"
/* IDENTIFICATION: *************************************************/
#define PROGRAM "tirrender"
#define VERSION "0.0"
#define COPYRIGHT "Copyright 2011 David Meyer"
#define CONTACT "David Meyer <
[email protected]>"
#define DESCRIPTION "tir HTML renderer for files and directories"
#define USAGE "Usage: tirrender [-hV] [-d <dataset>] [-l <location>] [-f <file>]"
/* CONSTANTS: ******************************************************/
/* MACROS: *********************************************************/
/* GLOBALS: ********************************************************/
/* PROTOTYPES: *****************************************************/
void msghelp ();
void msgversion ();
int parseopts PARAMS((int argc, char* argv[], int optstat, char *optarg[]));
/* MAIN: ***********************************************************/
/* main() parses and validates command line arguments, then calls
* render() if all OK.
*/
int main(argc, argv)
int argc;
char *argv[];
{
int optstat = 0; /* Specified options:
* Bit 0: -d (dataset)
* 1: -l (location)
* 2: -f (file)
* 3: -h (help)
* 4: -V (version)
*/
char *optarg[3]; /* Option arguments:
* [0]: -d (dataset)
* [1]: -l (location)
* [2]: -f (file)
*/
optstat = parseopts(argc, argv, optstat, optarg);
if (optstat & 8) { /* Arg. -h: display help, exit */
msghelp();
exit(0);
}
if (optstat & 16) { /* Arg. -V: display version, exit */
msgversion();
exit(0);
}
/* Arg. -d, <dataset> invalid:
* display error, exit
*/
if ((optstat & 1) && baddataset(optarg[0])) {
printf("Error: invalid dataset\n");
exit(1);
}
/* Arg. -l, <location> invalid:
* display error, exit
*/
if ((optstat & 2) && badlocation(optarg[1])) {
printf("Error: invalid location\n");
exit(1);
}
/* Arg. -f, <file> invalid:
* display error, exit
*/
if ((optstat & 4) && badfile(optarg[2])) {
printf("Error: invalid file\n");
exit(1);
}
/* Arg's OK: render specified
* object or default
*/
/* 2011-07-28
* "specified object": instead of separate location and file
* options, I could have single "object" option specified
* with the file/directory path relative to the dataset root.
* Use file status to determine file or directory rendering.
*/
return render((optstat & 1) ? optarg[0] : DEFAULT_DATASET,
(optstat & 2) ? optarg[1] : DEFAULT_LOCATION,
(optstat & 4) ? optarg[2] : DEFAULT_FILE);
}
/* FUNCTIONS: ******************************************************/
/* msghelp() - display help message
*/
void msghelp ()
{
printf("%s\n%s
-h Display this information
-V Display version
-d <dataset> Render target dataset
-l <location> Render target location (directory)
-f <file> Render target file\n", DESCRIPTION, USAGE);
}
/* msgversion() - display program version message
*/
void msgversion ()
{
printf("%s %s\n", PROGRAM, VERSION);
}
/* parseopts() - parse options in commnd line arguments
*/
int parseopts (argc, argv, optstat, optarg)
int argc;
char *argv[];
int optstat;
char *optarg[];
{
int a, n;
for (a = 1; a < argc; a++) { /* for each argument */
/* options d, l, f take arguments
* and must be specified
* individually.
* opt. arg. value is either
* string following opt. char.
* or next argument.
if (!strcmp(argv[a], "-d")) { /* arg. = -d: */
optstat = optstat | 1;
optarg[0] = (char *) malloc(strlen(argv[++a])+1);
strcpy(optarg[0], argv[a]);
}
/* arg. = -d*: */
else if (!strncmp(argv[a], "-d", 2)) {
optstat = optstat | 1;
optarg[0] = (char *) malloc(strlen(argv[a])-1);
strcpy(optarg[0], argv[a]+2);
}
/* arg. = -l: */
else if (!strcmp(argv[a], "-l")) {
optstat = optstat | 2;
optarg[1] = (char *) malloc(strlen(argv[++a])+1);
strcpy(optarg[1], argv[a]);
}
/* arg. = -l*: */
else if (!strncmp(argv[a], "-l", 2)) {
optstat = optstat | 2;
optarg[1] = (char *) malloc(strlen(argv[a])-1);
strcpy(optarg[1], argv[a]+2);
}
/* arg. = -f: */
else if (!strcmp(argv[a], "-f")) {
optstat = optstat | 4;
optarg[2] = (char *) malloc(strlen(argv[++a])+1);
strcpy(optarg[2], argv[a]);
}
/* arg. = -f*: */
else if (!strncmp(argv[a], "-f", 2)) {
optstat = optstat | 4;
optarg[2] = (char *) malloc(strlen(argv[a])-1);
strcpy(optarg[2], argv[a]+2);
}
else if (argv[a][0] == '-') { /* flag arg. (-*) */
/* for each char. in flag string */
for (n = 1; n < strlen(argv[a]); n++) {
if (argv[a][n] == 'h') { /* flag opt. h */
optstat = optstat | 8;
}
/* flag opt. V */
else if (argv[a][n] == 'V') {
optstat = optstat | 16;
}
else { /* unrecognized flag. opt. */
printf("Invalid option: -%c\n%s\n", argv[a][n], USAGE);
exit(0);
}
}
}
else { /* unrecognized arg.
* for compatibility with CGI
* query string format, c.l.
* I/F has no non-option args.
*/
printf("Invalid argument: %s\n%s\n", argv[a], USAGE);
exit(0);
}
}
return optstat;
}