PROGRAM 2
/****************************************************************************/
/* program: myuart2a.c */
/* author: anthony f. ortiz */
/* class: cs3590 */
/* date: febuary 25, 1999 */
/* description: serial chat program #2 (sender) */
/****************************************************************************/
#include
#include
#include
#include
#include
#include
#include "uart.h"
/* frame structure: start of header is the beginning of the frame and is */
/* equal to 1. */
/* sequence number is the number of the frame and starts */
/* at 1 and ends at 255 */
/* length is the number of characters in the data */
/* portion of the frame. */
/* data payload is the data portion of the frame. */
/* checksum is the addition of all the array elements in */
/* the frame. */
struct frame
{
byte_t start_of_header;
byte_t sequence_number;
byte_t length;
byte_t * data_payload;
byte_t checksum;
};
/* construct the frame. */
void construct_frame (struct frame *aframe, int file_descriptor, byte_t max_bytes)
{
/* for loop variable */
int i;
/* read 255 or less characters from the data file and fill in */
/* frame's length, start of header, and sequence number. */
aframe -> length = _read (file_descriptor, aframe -> data_payload, max_bytes);
aframe -> start_of_header = 0;
aframe -> sequence_number = aframe -> sequence_number + 1;
/* calculate the frame's checksum. */
aframe -> checksum = aframe -> start_of_header + aframe -> sequence_number +
aframe -> length;
for (i = 0; i < aframe -> length; i++)
{
aframe -> checksum = aframe -> checksum + aframe -> data_payload [i];
}
}
/* either corrupt the frame or don't corrupt the frame. */
void corrupt_bit (struct frame *aframe, int error_frequency)
{
/* if the frame count equals 2 * the error frequencey, */
/* corrupt the data by adding 1 to 1st element in data */
/* array. also, print out error message. otherwise, */
/* do nothing and print out a positive message. */
if (error_frequency == 0 || aframe -> sequence_number % error_frequency != 0)
{
printf ("there is no error in frame %i.\n", aframe -> sequence_number);
}
else
{
aframe -> data_payload [0] = aframe -> data_payload [0] + 1;
printf ("there is an error in frame %i.\n", aframe -> sequence_number);
}
}
/* send frame to receiver. */
void send_frame (struct frame aframe, int return_value, int port)
{
/* for loop variable */
int i;
/* send frame over the serial line. */
return_value = com_out (port, aframe.start_of_header);
return_value = com_out (port, aframe.sequence_number);
return_value = com_out (port, aframe.length);
for (i = 0; i < aframe.length; i++)
{
return_value = com_out (port, aframe.data_payload [i]);
}
return_value = com_out (port, aframe.checksum);
}
/* wait for some type of aknowledgement from receiver. */
void wait_aknowledgement (struct frame aframe, int return_value, int port, byte_t * mode)
{
/* initialize mode to -1 and wait for an acknowledgement. */
*mode = -1;
do
{
return_value = com_in (port, mode);
}
while (*mode != aframe.sequence_number && *mode != aframe.sequence_number - 1);
}
/* either uncorrupt the frame or don't uncorrupt the frame. */
void uncorrupt_bit (struct frame *aframe, byte_t mode)
{
/* if it is a positive acknowledgement, print acknowledgement */
/* message. otherwise print acknowledgement wasn't received */
/* and uncorrupt the first bit of data. */
if (mode == aframe -> sequence_number)
{
printf ("acknowledgement was received. frame %i is ok.\n", aframe -> sequence_number);
}
else
{
printf ("acknowledgement wasn't received. send frame %i again.\n", aframe -> sequence_number);
aframe -> data_payload [0] = aframe -> data_payload [0] - 1;
}
}
/* this program will read a file from disk and transfer it over the serial */
/* line using arq algorithm to overcome errors. */
void main ()
{
/* error frequency in the arq algorithm */
int error_frequency;
/* data file that is sent over the serial line */
char * infile;
/* file descriptor of data file */
int file_descriptor;
/* return value of com_open, in, out, and close functions */
int return_value;
/* port number for com_open, in, out, and close functions */
int port = 1;
/* mode of com_open, in, and out functions */
byte_t mode = BAUD9600 | PARITY_NONE | STOP1 | WORD_8BIT;
/* the frame being sent */
struct frame aframe;
/* maximum possible bytes to read from data file */
byte_t max_bytes = 255;
/* clear the screen. */
clrscr ();
/* initialize the uart. */
return_value = com_open (port, mode);
/* enter the frequency of errors and the name of the data file. */
printf ("enter frequency of errors (0 - 1000): ");
scanf ("%i", &error_frequency);
printf ("enter name of infile: ");
scanf ("%s", infile);
/* open the data file for reading. */
file_descriptor = open (infile, O_RDONLY);
if (file_descriptor == -1)
{
exit (1);
}
/* initialize frame's sequence number to 0. */
aframe.sequence_number = 0;
/* loop until frame length is less then maximum number of bytes. */
do
{
/* construct the frame. */
construct_frame (&aframe, file_descriptor, max_bytes);
/* either corrupt the frame or don't corrupt the frame. */
corrupt_bit (&aframe, error_frequency);
/* loop until there is a positive acknowledgement. */
do
{
/* send frame to receiver. */
send_frame (aframe, return_value, port);
/* wait for some type of aknowledgement from receiver. */
wait_aknowledgement (aframe, return_value, port, &mode);
/* either uncorrupt the frame or don't uncorrupt the frame. */
uncorrupt_bit (&aframe, mode);
}
while (mode != aframe.sequence_number);
}
while (aframe.length == max_bytes);
/* close the data file. */
close (file_descriptor);
/* close the uart. */
return_value = com_close (port);
}
/****************************************************************************/
/* program: myuart2b.c */
/* author: anthony f. ortiz */
/* class: cs3590 */
/* date: febuary 25, 1999 */
/* description: serial chat program #2 (receiver) */
/****************************************************************************/
#include
#include
#include
#include
#include
#include
#include "uart.h"
/* frame structure: start of header is the beginning of the frame and is */
/* equal to 1. */
/* sequence number is the number of the frame and starts */
/* at 1 and ends at 255 */
/* length is the number of characters in the data */
/* portion of the frame. */
/* data payload is the data portion of the frame. */
/* checksum is the addition of all the array elements in */
/* the frame. */
struct frame
{
byte_t start_of_header;
byte_t sequence_number;
byte_t length;
byte_t * data_payload;
byte_t checksum;
};
/* find start of header. */
void find_header (struct frame *aframe, int return_value, int port, byte_t *mode, int *count)
{
/* loop until start of header is found. */
do
{
return_value = com_in (port, mode);
}
while (*mode != 0);
/* initialize count which will stand for the bytes in our frame. */
/* also, start of header equals mode since it is equal to 0. */
*count = 1;
aframe -> start_of_header = *mode;
}
/* reconstruct frame (structure). */
void reconstruct_frame (struct frame *aframe, int *return_value, int port, byte_t *mode, int *count)
{
/* read uart. */
*return_value = com_in (port, mode);
if (*return_value >= 0)
{
*count = *count + 1;
}
/* add 1 to the count if there is something in uart. */
/* recontruct frame (structure) depending on count. */
if (*return_value >= 0 && *count == 2)
{
aframe -> sequence_number = *mode;
}
else if (*return_value >= 0 && *count == 3)
{
aframe -> length = *mode;
}
else if (*return_value >= 0 && *count >= 4 && *count <= 3 + aframe -> length)
{
aframe -> data_payload [*count - 4] = *mode;
}
else if (return_value >= 0 && *count == 4 + aframe -> length)
{
aframe -> checksum = *mode;
}
}
/* send some type of aknowledgement. */
void send_acknowledgement (struct frame aframe, int file_descriptor, int return_value, int port, int count, byte_t * checksum2)
{
/* for variable */
int i;
/* size of file for write function */
int size;
/* if count is equal to the last byte in the frame, then */
/* execute this if statement. */
if (return_value >= 0 && count > 3 && count == 4 + aframe.length)
{
/* calculate the frame's checksum. */
*checksum2 = aframe.start_of_header + aframe.sequence_number +
aframe.length;
for (i = 0; i < aframe.length; i++)
{
*checksum2 = *checksum2 + aframe.data_payload [i];
}
/* if checksum is correct, then print acknowlegment sent */
/* to the screen, write frame's data to the outfile, and */
/* send a postive acknowledgement over the serial line. */
/* otherwise, print acknowledgement not sent and send a */
/* negative acknowledgement (current frame # - 1) over */
/* the serial line. */
if (aframe.checksum == *checksum2)
{
printf ("frame %i is ok. send acknowledgement.\n", aframe.sequence_number);
size = _write (file_descriptor, aframe.data_payload, aframe.length);
return_value = com_out (port, aframe.sequence_number);
}
else
{
printf ("frame %i is corrupted. don't send acknowledgement.\n", aframe.sequence_number);
return_value = com_out (port, aframe.sequence_number - 1);
}
}
}
/* this program will read data from the serial port and write the file to */
/* disk. */
void main ()
{
/* data file */
char * outfile;
/* file descriptor of data file */
int file_descriptor;
/* return value for com_open, in, out, and close functions */
int return_value;
/* port number for com_open, in, out, and close functions */
int port = 1;
/* mode for com_open, in, and out functions */
byte_t mode = BAUD9600 | PARITY_NONE | STOP1 | WORD_8BIT;
/* frame (structure) being constructed from com_in */
struct frame aframe;
/* maximum possible bytes for writing to data file */
byte_t max_bytes = 255;
/* count used to reconstruct frame (structure) */
int count;
/* checksum on receiver's side */
byte_t checksum2;
/* clear the screen. */
clrscr ();
/* initialize the uart. */
return_value = com_open (port, mode);
/* enter the name of the data file. */
printf ("enter name of outfile: ");
scanf ("%s", outfile);
/* open the data file for writing. */
file_descriptor = open (outfile, O_CREAT | O_TEXT);
if (file_descriptor == -1)
{
exit (1);
}
/* loop until frame's length is less then maximum number of bytes. */
do
{
/* find start of header. */
find_header (&aframe, return_value, port, &mode, &count);
/* loop until the whole frame (structure) has been reconstructed. */
do
{
/* reconstruct frame (structure). */
reconstruct_frame (&aframe, &return_value, port, &mode, &count);
/* send some type of aknowledgement. */
send_acknowledgement (aframe, file_descriptor, return_value, port, count, &checksum2);
}
while (count != 4 + aframe.length);
}
while (aframe.length == max_bytes || aframe.checksum != checksum2);
/* close the data file. */
close (file_descriptor);
/* close uart. */
return_value = com_close (port);
}
/* filename: uart.h, uart.c */
/* see program 1. */
/* data file: infile.dat */
hi, anthony.
/* outfile: outfile.out */
hi, anthony.
/* outfile: prog2.out */
/* computer 1 */
enter frequency of errors (0 - 1000): 1
enter name of infile: infile.dat
there is an error in frame 1.
acknowledgement wasn't received. send frame 1 again.
acknowledgement was received. frame 1 is ok.
/* computer 2 */
enter name of outfile: outfile.out
frame 1 is corrupted. don't send acknowledgement.
frame 1 is ok. send acknowledgement.
BACK TO CS3590 PAGE.