SICE Curriculum Portal for Thomas Heffron
Contents

Home
UMKC Curriculum
   FS '96
      CS 101
   SS '01
      CS 201
   FS '01
      CS 191
      CS 281
   WS '02
      CS 291
      EN 304wi
   SS '02
      CS 352
      CS 481
   FS '02
      CS 431
      CS 441
   WS '03
      CS 423
      CS 451
SICE Survival Guide
Personal Experience

contact me @umkc:
tehqnf@umkc.edu

CS431 - Homework #6
 
/*********************************************
Name:     Thomas Heffron
Section:  CS431 NET
Program:  Program #6 - filter
Due Date: Dec. 5, 2002
Desc:     Process that opens an IPC input pipe
          to read from and creates an IPC output
          pipe to exportan 'encrypted' stream.
Inputs:   Process takes two CMD args as
          input/output pipe names.
Outputs:  Process will pass error signals
          if pipes cannot be opened.
**********************************************/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <signal.h>
#include <errno.h>
#include <time.h>

/* Data declarations used by all functions */
int inpipe, outpipe;
extern int errno;

/* Function declarations */
static void sig_alarm(int signo);
unsigned long get_time();

int main(int argc, char *argv[]) {
    int fifostat, size, wait_val, i;
    char buffer[256];
    size_t bsize = 256;
    umask(0);

    /* Set random seed */
    srand(get_time() % 32005);

    printf("Filter created...\n");

    /* Set alarm signal handlers - one for SIGUSR1 */
    if (signal(SIGUSR1, sig_alarm) == SIG_ERR) {
        printf("The SIGUSR1 function returned an error.\n");
        exit(1);
    }

    /* and one for SIGUSR2 */
    if (signal(SIGUSR2, sig_alarm) == SIG_ERR) {
        printf("The SIGUSR2 function returned an error.\n");
        exit(1);
    }

    /* Open pipe for reading - signal to main if error */
    if ( (inpipe = open(argv[1], 0666)) == -1) {
        printf("!!! Could not open pipe for input: %s\n", argv[1]);
        printf("!!! Sending alarm to main process.\n");
        kill(getppid(), SIGALRM);
    }

    /* Now open the pipe for writing - signal to main if error */
    if ( (outpipe = open(argv[2], 0666)) == -1) {
        printf("!!! Could not open pipe for output: %s\n", argv[2]);
        printf("!!! Sending alarm to main process.\n");
        kill(getppid(), SIGALRM);
    }

    /* Now begin to handle streams */
    /* Read until the single char EOF is read from input. */
    /* For each buffer chunk change each lower case to upper */
    /* and each upper case to lower. Then pass changed stream to */
    /* output pipe. Calculate a random time to wait */
    size = read(inpipe, buffer, 256);
    buffer[size] = '\0';
    while (buffer[0] != EOF) {
        for(i = 0; i < size; i++) {
            if ((buffer[i] >= 'a') && (buffer[i] <= 'z'))
                buffer[i] = (buffer[i] - 'a' + 'A');
            else if ((buffer[i] >= 'A') && (buffer[i] <= 'Z'))
                buffer[i] = (buffer[i] - 'A' + 'a');
        }
        printf("%s", buffer);
        write(outpipe, buffer, strlen(buffer));
        wait_val = ((int) (4.0*rand()/(RAND_MAX + 1.0)));
        sleep(wait_val);
        size = read(inpipe, buffer, 256);
        buffer[size] = '\0';
    }

    /* Once pipe is 'empty' send a single EOF to output */
    buffer[0] = EOF;
    write(outpipe, buffer, 1);
       
    /* now wait until this process gets the alarm from main */
    /* Main will then send signals to this process for exit */
    while(1);
}

/* Single function to handle all signals */
static void sig_alarm(int signo) {
    /* if signal is USER1 then simply wait */
    /* we do this to stop processing input */
    /* but wait for other processes to stop */
    if (signo == SIGUSR1) {
        printf("* Filter halted.\n");
        while(1);
    }

    /* if signal is USER2 then main has */
    /* handled the exit gracefully. we will */
    /* close all pipes and exit process. */
    if (signo == SIGUSR2) {
        close(inpipe);
        close(outpipe);
        printf("** Filter now exiting.\n");
        exit(0);
    }
}

/* Function to get large integer for random seed */
unsigned long get_time()
{
    FILE *in_file;
    unsigned long retval;
    float trash;

    in_file = fopen("/proc/uptime", "r");
    fscanf(in_file, "%lu%f", &retval, &trash);

    fclose(in_file);
 
    return retval;
}