Download | Plain Text | Line Numbers
/*
* Name: mycat
* Author: Manuel Mausz, 0728348
* Description: A simplified version of cat
* Created: 11.03.2009
* Exercise: 1h A
*/
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
/* global variables */
char *me; /* name of myself (argv[0]) */
int vflag = 0; /* cmdline option: -v set */
int eflag = 0; /* cmdline option: -e set */
int tflag = 0; /* cmdline option: -t set */
/*
* NAME: scan
* PURPOSE:
* reads characters from stream, converts them according the
* commandline options and print the converted characters on stdout
*
* PARAMETERS:
* FILE *fp ... pointer to a stream to read from
*
* RETURN VALUE:
* void
*
* GLOBAL VARS:
* vflag, eflag, tflag
*/
void scan(FILE *fp)
{
int ch;
while((ch = getc(fp)) != EOF)
{
/* eflag: print '$' before '\n' */
if (ch == '\n')
{
if (eflag && putchar('$') == EOF)
break;
}
/* tflag: print '^I' instead of '\t' */
else if (ch == '\t')
{
if (tflag)
{
if (putchar('^') == EOF || putchar('I') == EOF)
break;
continue;
}
}
/* vflag */
else if (vflag)
{
/* 128 <= ch <= 255: print 'M-'.(ch-128) */
if (128 <= ch && ch <= 255)
{
if (putchar('M') == EOF || putchar('-') == EOF)
break;
ch = ch - 128;
}
/* 0 <= ch <= 31: print '^'.(ch+'@') */
if (0 <= ch && ch <= 31)
{
if (putchar('^') == EOF || putchar(ch + '@') == EOF)
break;
continue;
}
/* ch == 27: print '^?' */
else if (ch == 127)
{
if (putchar('^') == EOF || putchar('?') == EOF)
break;
continue;
}
}
/* print character to stdout */
if (putchar(ch) == EOF)
break;
}
}
/*
* NAME: usage
* PURPOSE:
* prints program usage to stderr and terminates with EXIT_FAILURE
*
* PARAMETERS:
* void
*
* RETURN VALUE:
* void
*
* GLOBAL VARS:
* me
*/
static void usage(void)
{
(void) fprintf(stderr, "Usage: %s [-vET]\n", me);
(void) exit(EXIT_FAILURE);
}
/*
* NAME: main
* PURPOSE:
* parses commandline options and calls scan()
*
* PARAMETERS:
* standard parameters of main(...)
*
* RETURN VALUE:
* int ... always 0
*
* GLOBAL VARS:
* me, vflag, eflag, tflag
*/
int main(int argc, char *argv[])
{
int opt;
me = argv[0];
while ((opt = getopt(argc, argv, "vET")) != -1)
{
switch(opt)
{
case 'v':
vflag = 1;
break;
case 'E':
eflag = 1;
break;
case 'T':
tflag = 1;
break;
default:
(void) usage();
break;
}
}
(void) scan(stdin);
return 0;
}
/* vim: set et sw=2 ts=2: */