diff options
author | Tucker Evans <tuckerevans24@gmail.com> | 2019-02-18 07:35:54 -0500 |
---|---|---|
committer | Tucker Evans <tuckerevans24@gmail.com> | 2019-02-18 07:35:54 -0500 |
commit | e8b1808eaf87a49e4c34ebbfb66854baa627418c (patch) | |
tree | 8a4bb15321992702b6b26e34bd2ed3a55bb7b0d9 /CS3871 | |
parent | 6cc5652a8af3361288393718ec2adb2889c9af1e (diff) |
Moves assignments to given course folder.
Diffstat (limited to 'CS3871')
-rw-r--r-- | CS3871/filesystem/README.rst | 0 | ||||
-rw-r--r-- | CS3871/filesystem/disk.h | 17 | ||||
-rw-r--r-- | CS3871/filesystem/disk.o | bin | 0 -> 3352 bytes | |||
-rw-r--r-- | CS3871/filesystem/tfs.c | 352 | ||||
-rw-r--r-- | CS3871/jobScheduler/cpuScheduleTable.c | 224 | ||||
-rw-r--r-- | CS3871/sync/assign.rst | 41 | ||||
-rw-r--r-- | CS3871/sync/makefile | 5 | ||||
-rw-r--r-- | CS3871/sync/reader.c | 86 | ||||
-rw-r--r-- | CS3871/sync/sync.c | 118 | ||||
-rw-r--r-- | CS3871/sync/writer.c | 76 | ||||
-rw-r--r-- | CS3871/timing/client.c | 133 |
11 files changed, 1052 insertions, 0 deletions
diff --git a/CS3871/filesystem/README.rst b/CS3871/filesystem/README.rst new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/CS3871/filesystem/README.rst diff --git a/CS3871/filesystem/disk.h b/CS3871/filesystem/disk.h new file mode 100644 index 0000000..7bf6ad0 --- /dev/null +++ b/CS3871/filesystem/disk.h @@ -0,0 +1,17 @@ +#include <stdio.h> +#include <string.h> +#include <stdlib.h> + +#define TRACKS 128 +#define SECTORS 4096 + +/* 10ms per track change */ +/* 10ms/SECTORS per unit sector distance > 1 */ + +void dinit(); + +void rsector(int t,int s,unsigned char *b); + +void wsector(int t,int s,unsigned char *b); + + diff --git a/CS3871/filesystem/disk.o b/CS3871/filesystem/disk.o Binary files differnew file mode 100644 index 0000000..b1a36f8 --- /dev/null +++ b/CS3871/filesystem/disk.o diff --git a/CS3871/filesystem/tfs.c b/CS3871/filesystem/tfs.c new file mode 100644 index 0000000..fe2d94c --- /dev/null +++ b/CS3871/filesystem/tfs.c @@ -0,0 +1,352 @@ +#include <stdlib.h> +#include <stdio.h> +#include <string.h> +#include <sys/time.h> +#include "disk.h" + +#define MAX_INODES 1000 +#define INODE_START (TRACKS * SECTORS) / (8 * 512) +#define MAX_FILES 50 + +struct block_ptr { + char track; + short sector; +}; +struct blockll{ + struct block_ptr data; + struct blockll *next; +}; + +struct meta_data{ + char name[8]; + int size; + int read; + int write; + int create; +}; + +struct inode { + struct meta_data info; + struct block_ptr data[20]; +}; + + +struct inode_list{ + struct inode *node; + struct inode_list *next; +}; + +struct file { + struct inode *node; + int mode; + int next_sec; + int free; +}; + + +int inode_list_size = 0; +struct inode_list *root, *end; + +char bitmap[TRACKS][SECTORS/8]; + +struct file files[MAX_FILES]; +int size; + + + +int check_bitmap(t,s) +int t,s; +{ + char tmp; + tmp = bitmap[t][s/8]; + tmp &= (1 << (s % 8)); + return (int) tmp; +} + +void set_bitmap(t,s) +int t,s; +{ + bitmap[t][s/8] |= (1 << (s % 8)); + return; +} + +void print_bitmap() +{ + int i,j; + for(i = 0; i < 128; i++){ + + printf("\n%4d ", i); + for (j = 0; j < 4096/8; j++) { + printf("%02x", bitmap[i][j]); + if (j %31 == 0) { + printf("\n%4d ",i); + } + } + } +} + + +/* TODO + * Implement inode table as binary tree to speedup searches + */ +struct inode* inode_search(name) +char *name; +{ + if (strcmp(name,"") == 0) { + return -1; + } + int i; + struct inode_list *tmp = root; + + for(i = 0; i < MAX_INODES && i < inode_list_size; i++){ + tmp = tmp->next; + if(strcmp(name, tmp->node->info.name) == 0) + return tmp->node; + } + return -2; +} + +struct blockll* get_blocks(size) +int size; +{ + int i, t, s; + struct blockll *root, *current = malloc(sizeof(struct blockll)); + root = current; + + for (i = 0; size > 0 && i < (4096 * 128); i++) { + t = i / 4096; + s = i % 4096; + + if (!check_bitmap(t, s)) { + current->next = malloc(sizeof(struct blockll)); + current = current->next; + current-> next = NULL; + current->data.track = (char) t; + current->data.sector = (short) s; + + set_bitmap(t,s); + size-= 512; + } + } + + return i <(4096 * 128) ? root : NULL; +} + +struct inode_list* inode_create(name) +char *name; +{ + struct timeval *tmp_time = malloc(sizeof(struct timeval)); + + struct inode_list *tmp = malloc(sizeof(struct inode_list)); + struct inode *tmp_node = malloc(sizeof(struct inode)); + + + tmp->node = tmp_node; + + memcpy(&(tmp->node->info.name), name, strlen(name)); + + gettimeofday(tmp_time, NULL); + + tmp->node->info.create = tmp_time->tv_sec; + tmp->node->info.read = tmp_time->tv_sec; + tmp->node->info.write = tmp_time->tv_sec; + + end->next = tmp; + end = tmp; + inode_list_size++; + + return tmp; +} + +int inode_init() +{ + int n = MAX_INODES / 4; + int i; + char *ptr; + struct inode_list *tmp; + + if (MAX_INODES % 4 > 0) + n++; + + char *buf = malloc(512 * n); + + for (i =0; i < n; i++) { + rsector(0, i, buf + (512 * i)); + } + ptr = buf; + + tmp = root; + + for(i=0; i< MAX_INODES; i++) { + tmp->next = malloc(sizeof(struct inode_list)); + memcpy(&tmp->node, ptr, 64); + ptr += 64; + tmp = tmp->next; + inode_list_size++; + } +} + +/*save inodes to first n sectors on disk*/ +void inode_save() +{ + int i, j; + char *buf = malloc(512); + struct inode_list *tmp = root; + + for (i = 0; i < MAX_INODES && tmp->next;i++) { + for (j = 0; j < 4; j++){ + tmp = tmp->next; + memcpy(buf + j, tmp->node, sizeof(struct inode)); + } + wsector(0, INODE_START + i, buf); + } +} + +struct inode* inode_from_fd(fd) +int fd; +{ + int i; + struct inode_list *tmp = root; + + for (i = 0; i < fd; i++) { + tmp = tmp->next; + } + + return tmp->node; +} + +int find_fd() +{ + int i; + for (i = 0; i < size; i++) { + if (files[i].free) + return i; + } +} + +int tfs_init() +{ + int i; + root = malloc(sizeof(struct inode_list)); + end = root; + + dinit(); + /* + * + * has issue if inodes have not been written to disk i.e. first run + inode_init(); + */ + for (i = 0; i < MAX_FILES; i++) { + files[i].free = 1; + } +} + + +int open(fname, mode) +char *fname, *mode; +{ + struct inode *fnode = inode_search(fname); + int fd; + + if (fnode == -1) + return -1; + + if (fnode == -2){ + fnode = inode_create(fname)->node; + } + fd = find_fd(); + + files[fd].node = fnode; + files[fd].mode = *mode; + files[fd].next_sec = 0; + files[fd].free = 0; + size++; + + return fd; +} + +int close(fd) +int fd; +{ + if (files[fd].free) + return -1; + + files[fd].free = 1; + return 1; +} + +int read(fd, buf) +int fd; +char *buf; +{ + if (files[fd].free || files[fd].mode || (files[fd].next_sec == 20)) + return -1; + + + rsector(files[fd].node->data[files[fd].next_sec].track, files[fd].node->data[files[fd].next_sec].sector, buf); + files[fd].next_sec++; + return 512; +} + +int write(fd, buf) +int fd; +char *buf; +{ + if ((files[fd].next_sec == 20) || !files[fd].mode) + return 0; + + struct blockll *tmp = get_blocks(500); + files[fd].node->data[files[fd].next_sec].track = tmp->data.track; + files[fd].node->data[files[fd].next_sec].sector = tmp->data.sector; + + wsector(files[fd].node->data[files[fd].next_sec].track, files[fd].node->data[files[fd].next_sec].sector, buf); + return 1; +} + +int ulink(fname) +char *fname; +{ + struct inode_list *tmp = root; + struct inode *d; + int i; + + for(i = 0; i < MAX_INODES && i < inode_list_size; i++){ + tmp = tmp->next; + if(strcmp(fname, tmp->next->node->info.name) == 0) + break;; + } + + d = tmp->next->node; + tmp->next = tmp->next->next; + free(d); + return 1; + } + +int main() +{ + tfs_init(); + + /* + *Test Writing + */ + int mode = 1; + int fd = open("test", &mode); + + char buf[512]; + memcpy(&buf, "Hello Filesystem", strlen("Hello Filesystem")); + + int test = write(fd, &buf); + close(fd); + + /* + *Test reading + */ + mode = 0; + fd = open("test", &mode); + char buf2[512]; + read(fd, &buf2); + printf("wrote: %s\n", buf); + + printf("read: %s\n", buf2); + +} diff --git a/CS3871/jobScheduler/cpuScheduleTable.c b/CS3871/jobScheduler/cpuScheduleTable.c new file mode 100644 index 0000000..5d2256a --- /dev/null +++ b/CS3871/jobScheduler/cpuScheduleTable.c @@ -0,0 +1,224 @@ +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <sys/types.h> +#include <unistd.h> +#include <signal.h> +#include <sys/time.h> + +#define PROCESS_COUNT 4 +#define time_calc(x, y) ((y.tv_sec - x.tv_sec) * 1000000) + (y.tv_usec - x.tv_usec) + + +/* TODO +add heap for priority +compute priority +*/ + +int go=1; +int turn=0; +float v; +float throughput; +struct timeval start_time; +int turns; +int completed_jobs; + +struct process { + int virgin; + int (*proc)(int); + int turnaround[9]; + struct timeval start_t; + int runs; + float save; + int turn; +}; + +struct process pt[PROCESS_COUNT]; /*process table*/ + +void +cpusched(signum) +int signum; +{ + pt[turn].virgin=0; + pt[turn].save=v; + go=0; +} + +int +f0(x) +int x; +{ + register int i=0; + register int t; + signal(SIGUSR1, cpusched); + if (!x) goto start; + v=0.0; + +start: + while (go && (v > -200.0)) { + printf("0");fflush(stdout); + t = (rand() % 1024); + v -= 2.0; + if ((v>0.0) || ((((int) v) % 2) == -1)) { + printf("f0, found odd or positive, v= %f\n", v); + exit(1); + } + usleep(t*100); + } + if (v <= -200.0) pt[0].virgin=1; + go=1; +} + +int +f1(x) +int x; +{ + register int i=0; + register int t; + if (!x) goto start2; + v= -1.0; + +start2: + while (go && (v > -401.0)) { + printf("1");fflush(stdout); + t = (rand() % 2048); + v -= 2.0; + if ((v>0.0) || ((((int) v) % 2) != -1)) { + printf("f1, found even or positive\n"); + exit(1); + } + usleep(t*100); + } + if (v <= -401.0) pt[1].virgin=1; + go=1; +} + +int +f2(x) +int x; +{ + register int i=0; + register int t; + if (!x) goto start3; + v= 1.0; + +start3: + while (go) { + printf("2");fflush(stdout); + t = (rand() % 4096); + v += 2.0; + if ((v<0.0) || ((((int) v) % 2) != 1)) { + printf("f2, found even or negative\n"); + exit(1); + } + usleep(t*100); + } + go=1; +} + +int +f3(x) +int x; +{ + register int i=0; + register int t; + if (!x) goto start4; + v= 0.0; + +start4: + while (go) { + printf("3");fflush(stdout); + t = (rand() % 4096); + v += 2.0; + if ((v<0.0) || ((((int) v) % 2) == 1)) { + printf("f3, found odd or negative\n"); + exit(1); + } + usleep(t*100); + } + go=1; +} + +void turnaround_calc(p, n) +struct process *p; +int n; +{ + int i; + p->turnaround[8] = 0; + for (i = 0; i < n; i++) { + p->turnaround[8] += p->turnaround[i] / n; + } + return; +} + +int main(argc, argv, envp) +int argc; +char **argv, **envp; +{ + int pid, i, last; + struct timeval end_t; + gettimeofday(&start_time, NULL); + + for (i = 0; i < PROCESS_COUNT; i++) { + pt[i].virgin = 1; + } + + pt[0].proc=f0; + pt[1].proc=f1; + pt[2].proc=f2; + pt[3].proc=f3; + + signal(SIGUSR1, cpusched); + if (pid=fork()) { + while (1) { + go = 1; + sleep(5); + if (go) + kill(pid, SIGUSR1); + } + } else { + while (1) { + printf("turn= %d\n", ++turns); + v=pt[turn].save; + if (pt[turn].virgin) + gettimeofday(&pt[turn].start_t, NULL); + + pt[turn].proc(pt[turn].virgin); + + gettimeofday(&end_t, NULL); + + if (pt[turn].virgin) { + pt[turn].turnaround[pt[turn].runs % 8] = time_calc(pt[turn].start_t, end_t); + turnaround_calc(&pt[turn], (pt[turn].runs < 8 ? pt[turn].runs + 1 : 8)); + pt[turn].runs++; + completed_jobs++; + kill(getppid(), SIGUSR1); + } else if (pt[turn].runs == 0){ + pt[turn].turnaround[8] = (time_calc(pt[turn].start_t, end_t)) / 2; + } + + throughput = completed_jobs / (float)(end_t.tv_sec - start_time.tv_sec); + pt[turn].turn++; + + if (turns == 1000) { + kill(getppid(), 9); + exit(1); + } + + printf("\n"); + + for (i = 0; i < 4; i++){ + printf("\t[%d]\tturnaround= %9d\truns= %3d\tturn= %d\n", i, pt[i].turnaround[8], pt[i].runs, pt[i].turn); + } + + printf("\ntime= %5d\tthroughput= %9f\tcompleted_jobs= %d\n\n\n", end_t.tv_sec - start_time.tv_sec, throughput, completed_jobs); + + last = turn; + turn = 0; + for (i = 1; i < PROCESS_COUNT; i++) { + turn = ((pt[turn].turnaround[8] < pt[i].turnaround[8]) && (turn != last)) ? turn : i; + } + + } + } +} diff --git a/CS3871/sync/assign.rst b/CS3871/sync/assign.rst new file mode 100644 index 0000000..ea4a566 --- /dev/null +++ b/CS3871/sync/assign.rst @@ -0,0 +1,41 @@ +================ +Syncronization 1 +================ + +Write a program that uses semaphores to implement a readers/writers solution. Your program should: + + - be written in C and use the standard kernel IPC mechanisms (semget,semop,shmget etc) + - be written as a single top level source file compiled as: gcc –o myprog myprog.c + - take two arguments on the command line: myprog NR NW where NR,NW are each integers specifying the number of reader/writer processes respectively + - use fork/exec to create the readers/writers + +The shared memory segment should be 16k bytes in size, with all bytes initialized to 0x30 + +Reader: + +.. code :: + + open a file (for append) named reader.N, where N is the reader number + while (1) { + for (i=0; i<16k; i++) { + read the next byte of the shared memory segment + write that byte to the file + flush the file + } + sleep a random number of seconds, between 0 and N inclusive + } + +Writer: + +.. code :: + + while (1) { + for (i=0; i<16k; i++) + shared memory segment[i] = N + 0x30; + sleep a random number of seconds between 0 and 2*N inclusive + } + +readers and writers should be mutually exclusive +multiple concurrent readers are allowed +writers have priority over readers +writers are mutually exclusive relative to each other diff --git a/CS3871/sync/makefile b/CS3871/sync/makefile new file mode 100644 index 0000000..dd9c463 --- /dev/null +++ b/CS3871/sync/makefile @@ -0,0 +1,5 @@ +sync: sync.c reader.c writer.c + cc -o sync sync.c + cc -o reader reader.c + cc -o writer writer.c + diff --git a/CS3871/sync/reader.c b/CS3871/sync/reader.c new file mode 100644 index 0000000..929eba1 --- /dev/null +++ b/CS3871/sync/reader.c @@ -0,0 +1,86 @@ +#include <errno.h> +#include <signal.h> +#include <stdio.h> +#include <stdlib.h> +#include <sys/ipc.h> +#include <sys/select.h> +#include <sys/sem.h> +#include <sys/shm.h> +#include <sys/types.h> +#include <time.h> +#include <unistd.h> + +#define NSEM 3 +#define KEY 52 + +char *mem; + +void quit(signum) +int signum; +{ + shmdt(mem); + exit(1); +} + +int main(argc, argv) +int argc; +char **argv; +{ + int shmid, semid, i, pid, id; + char filename[50]; + FILE *fd; + struct sembuf sb; + + if (argc < 2) { + printf("usage: reader [id]\n"); + exit(1); + } + + id = atoi(argv[1]); + + + if ((shmid = shmget(52, 1<<14, IPC_CREAT | 0666)) == -1){ + perror("shmget: shmget failed"); + exit(1); + } + + if ((mem = shmat(shmid, NULL, 0)) == (char *) -1) { + perror("shmat"); + exit(1); + } + + if ((semid = semget(shmid, NSEM, 0)) == -1) { + perror("Rsemget: "); + exit(1); + } + + signal(SIGQUIT, quit); + + sprintf(filename, "reader.%d", id); + + fd = fopen(filename, "a"); + + if (!fd) { + perror("fopen: "); + exit(1); + } + srand(time(NULL)); + + while (1) { + sb.sem_num = 0; sb.sem_op = -1; sb.sem_flg = 0; + semop(semid, &sb, 1); + + for (i = 0; i < 1<<14; i++) { + fprintf(fd, "%c", *(mem + i)); + fflush(fd); + } + fprintf(fd, "\n"); + fflush(fd); + + sb.sem_op = 1; + semop(semid, &sb, 1); + + + sleep(rand() % (id + 1)); + } +} diff --git a/CS3871/sync/sync.c b/CS3871/sync/sync.c new file mode 100644 index 0000000..23d6ba1 --- /dev/null +++ b/CS3871/sync/sync.c @@ -0,0 +1,118 @@ +#include <stdio.h> +#include <stdlib.h> +#include <sys/ipc.h> +#include <sys/sem.h> +#include <sys/shm.h> +#include <sys/types.h> +#include <sys/wait.h> +#include <unistd.h> + +#define NSEM 3 + +union semun { + int val; + struct semid_ds *buf; + ushort *array; +}; + + +int shmid, semid; + +void quit(signum) +int signum; +{ + shmctl(shmid, IPC_RMID, NULL); + semctl(semid, IPC_RMID, 0); +} + + +int main(argc, argv) +int argc; +char **argv; +{ + int i, pid, n_read, n_write, w; + char *mem, **arg_r, **arg_w; + union semun semarg; + + if (argc < 2) { + printf("usage: sync [number readers] [number writers]\n"); + exit(1); + } + n_read = atoi(argv[1]); + n_write = atoi(argv[2]); + + if ((shmid = shmget(52, 1<<14, IPC_CREAT | 0666)) == -1){ + perror("shmget: shmget failed"); + exit(1); + } + + if ((mem = shmat(shmid, NULL, 0)) == (char *) -1) { + perror("shmat"); + exit(1); + } +printf("Sshmid: %x\n", shmid); + signal(SIGQUIT, quit); + + for (i = 0; i < 1<<14; i++) { + *(mem + i) = 0x30; + } + + if ((semid = semget(shmid, NSEM, 0666 | IPC_CREAT)) == -1) { + perror("Ssemget: "); + exit(1); + } + + semarg.val = 1; + for (i = 0; i < NSEM; i++) { + if ((semctl(semid, i, SETVAL, semarg)) == -1) { + perror("semctl: "); + exit(1); + } + } + + + arg_r = malloc(sizeof(char*) * 3); + arg_w = malloc(sizeof(char*) * 3); + *arg_r = malloc(sizeof(char) * 10); + *arg_w = malloc(sizeof(char) * 10); + + *(arg_r + 1) = malloc(sizeof(char) * 50); + *(arg_w + 1) = malloc(sizeof(char) * 50); + + *arg_r = "reader"; + *arg_w = "writer"; + + *(arg_r + 2) = NULL; + *(arg_w + 2) = NULL; + + for (i = 0; i < n_read; i++){ + sprintf(*(arg_r + 1), "%d", i); + if (pid = fork()) { + /* printf("starting reader %d...\n", i); */ + } else { + int ret = execv("./reader", arg_r); + printf("exec retern %d", ret); + } + } + + for (i = 0; i < n_write; i++) { + sprintf(*(arg_w + 1), "%d", i); + if (pid = fork()) { + /* printf("starting writer %d...\n", i); */ + } else { + execvp("./writer", arg_w); + } + + } + + shmdt(mem); +printf("sync done...\n"); +/* TODO + * why is this returning 8 + */ + for (i = 0; i < (n_write + n_read); i++) { + wait(&w); + printf("\nReturned with code:%d\n", WEXITSTATUS(w)); + } + quit(); +} diff --git a/CS3871/sync/writer.c b/CS3871/sync/writer.c new file mode 100644 index 0000000..d38dd70 --- /dev/null +++ b/CS3871/sync/writer.c @@ -0,0 +1,76 @@ +#include <errno.h> +#include <signal.h> +#include <stdio.h> +#include <stdlib.h> +#include <sys/ipc.h> +#include <sys/select.h> +#include <sys/sem.h> +#include <sys/shm.h> +#include <sys/types.h> +#include <sys/types.h> +#include <time.h> +#include <unistd.h> + +#define NSEM 3 + +char *mem; + +void quit(signum) +int signum; +{ + shmdt(mem); + exit(1); +} + +int main(argc, argv) +int argc; +char **argv; +{ + int shmid, semid, i, pid, id; + char *mem; + struct sembuf sb; + + if (argc < 2) { + printf("usage: writer [id]\n"); + exit(1); + } + + id = atoi(argv[1]); + + + if ((shmid = shmget(52, 1<<14, IPC_CREAT | 0666)) == -1){ + perror("shmget: shmget failed"); + exit(1); + } + + if ((mem = shmat(shmid, NULL, 0)) == (char *) -1) { + perror("shmat"); + exit(1); + } +printf("Wshmid: %x\n", shmid); + + if ((semid = semget(shmid, NSEM, 0)) == -1) { + perror("Wsemget: "); + exit(1); + } + + signal(SIGQUIT, quit); + + srand(time(NULL)); + + while (1) { + rand() % id; + + sb.sem_num = 0; sb.sem_op = -1; sb.sem_flg = 0; + semop(semid, &sb, 1); + + for (i = 0; i < 1<<14; i++) { + mem[i]= 0x30 + id; + } + + sb.sem_op = 1; + semop(semid, &sb, 1); + + sleep(rand() % ((id * 2) + 1)); + } +} diff --git a/CS3871/timing/client.c b/CS3871/timing/client.c new file mode 100644 index 0000000..9a83a5b --- /dev/null +++ b/CS3871/timing/client.c @@ -0,0 +1,133 @@ +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <sys/time.h> +#include <sys/socket.h> +#include <netinet/in.h> +#include <sys/select.h> + +#define BUFFER_SIZE 1024 + +typedef struct number_val { + int val; + struct timeval tv; +} num; + +int sock_init(argv) +char **argv; +{ + struct sockaddr_in address, serv_addr; + int sock = 0, valread; + char buffer[1024] = {0}; + + if ((sock = socket(AF_INET, SOCK_STREAM, 0)) < 0) { + perror("Socket creation error\n"); + return -1; + } + + memset(&serv_addr, '0', sizeof(serv_addr)); + + serv_addr.sin_family = AF_INET; + serv_addr.sin_port = htons(atoi(argv[2])); + + if (inet_pton(AF_INET, argv[1], &serv_addr.sin_addr) <= 0) { + perror("Invalid address/Address not supported\n"); + return -1; + } + + if (connect(sock, (struct sockaddr *) &serv_addr, sizeof(serv_addr)) < 0) { + perror("Connection Failed"); + return -1; + } + return sock; +} + +int main(argc, argv) +int argc; +char **argv; +{ + int sock = 0, valread, start_ptr = -1, end_ptr = 0, qset, i; + double avg = 0, cnt; + char buffer[1024] = {0}; + num num_buffer[BUFFER_SIZE]; + fd_set rs, ws, es; + struct timeval now, *ww, tmp; + + sock = sock_init(argv); + + ww = NULL; + + printf("Connected, waiting for numbers...\n"); + while (1) { + FD_ZERO(&rs); FD_ZERO(&ws); FD_ZERO(&es); + FD_SET(sock, &rs); + + qset = select(sock + 1, &rs, (fd_set *) 0, (fd_set *) 0, ww); + + gettimeofday(&now, NULL); + now.tv_sec = now.tv_sec - 60; + + ww = &tmp; + tmp.tv_sec = 0; + tmp.tv_usec = 500000; + + if (FD_ISSET(sock, &rs)) { + valread = read(sock, buffer, 1024); + for (i = 0; i < valread; i+=2) { + if (end_ptr == BUFFER_SIZE) + end_ptr = 0; + if (end_ptr != start_ptr) { + gettimeofday(&(num_buffer[end_ptr].tv), NULL); + num_buffer[end_ptr].val = atoi(buffer + i); + end_ptr++; + } else { + printf("dropping number...\n"); + } + } + } + + if (start_ptr == -1) + start_ptr = 0; + + if (start_ptr < end_ptr) { + for (i = start_ptr; i < end_ptr; i++) { + if (num_buffer[i].tv.tv_sec <= now.tv_sec) + start_ptr = i + 1; + } + } else { + for (i = start_ptr; i < BUFFER_SIZE; i++) { + num_buffer[end_ptr].val = atoi(buffer); + end_ptr++; + num_buffer[end_ptr].val = atoi(buffer); + end_ptr++; + num_buffer[end_ptr].val = atoi(buffer); + end_ptr++; + if (num_buffer[i].tv.tv_sec <= now.tv_sec) + start_ptr = i + 1; + } + + for (i = 0; i < end_ptr; i++) { + if (num_buffer[i].tv.tv_sec <= now.tv_sec) + start_ptr = i + 1; + } + + start_ptr %= BUFFER_SIZE; + } + + avg = 0; + cnt = start_ptr > end_ptr ? (BUFFER_SIZE - start_ptr + end_ptr) : (end_ptr - start_ptr); + cnt = cnt == 0 ? 10 : cnt; + + if (start_ptr < end_ptr) { + for (i = start_ptr; i < end_ptr; i++) + avg += num_buffer[i].val / cnt; + } else { + for (i = start_ptr; i < BUFFER_SIZE; i++) + avg += num_buffer[i].val / cnt; + for (i = 0; i < end_ptr; i++) + avg += num_buffer[i].val /cnt; + } + + printf("avg: %10.5f\n", avg); + } +} |