diff --git a/hw4/include/program.h b/hw4/include/program.h new file mode 100644 index 0000000..f72df4a --- /dev/null +++ b/hw4/include/program.h @@ -0,0 +1,14 @@ +typedef struct prog_data +{ + STMT *stmt; + struct prog_data *prev; + struct prog_data *next; +} prog_data; + +prog_data *prog_head; +prog_data *prog_counter; + +void prog_init(); +void prog_fini(); +prog_data *prog_get_data(int lineno); +void prog_remove_data(prog_data* data); diff --git a/hw4/include/store.h b/hw4/include/store.h index 275fabd..b460195 100644 --- a/hw4/include/store.h +++ b/hw4/include/store.h @@ -6,7 +6,7 @@ typedef struct store_data struct store_data *next; } store_data; -store_data *head; +store_data *store_head; void store_init(); store_data* store_get_data(char* var); diff --git a/hw4/src/jobs.c b/hw4/src/jobs.c index 19ec671..87573b8 100644 --- a/hw4/src/jobs.c +++ b/hw4/src/jobs.c @@ -12,6 +12,7 @@ #include "mush.h" #include "debug.h" #include "store.h" +#include "program.h" /* * This is the "jobs" module for Mush. @@ -49,6 +50,7 @@ */ int jobs_init(void) { store_init(); + prog_init(); return 0; } @@ -63,7 +65,9 @@ int jobs_init(void) { * @return 0 if finalization is completely successful, otherwise -1. */ int jobs_fini(void) { + // TODO cancel jobs, wait for terminate store_fini(); + prog_fini(); return 0; } @@ -85,7 +89,7 @@ int jobs_fini(void) { */ int jobs_show(FILE *file) { // TO BE IMPLEMENTED - abort(); + return 0; } /** diff --git a/hw4/src/main.c b/hw4/src/main.c index ca5b15a..364248b 100644 --- a/hw4/src/main.c +++ b/hw4/src/main.c @@ -5,6 +5,7 @@ #include "mush.h" #include "store.h" +#include "program.h" int main(int argc, char *argv[]) { jobs_init(); diff --git a/hw4/src/program.c b/hw4/src/program.c index e6379b3..30ed82c 100644 --- a/hw4/src/program.c +++ b/hw4/src/program.c @@ -3,6 +3,7 @@ #include "mush.h" #include "debug.h" +#include "program.h" /* * This is the "program store" module for Mush. @@ -25,8 +26,17 @@ * @return 0 if successful, -1 if any error occurred. */ int prog_list(FILE *out) { - // TO BE IMPLEMENTED - abort(); + prog_data *ptr = prog_head->next; + while (1) + { + if (ptr == prog_counter) + fprintf(out, "-->\n"); + if (ptr == prog_head) + break; + show_stmt(out, ptr->stmt); + ptr = ptr->next; + } + return 0; } /** @@ -47,8 +57,30 @@ int prog_list(FILE *out) { * @return 0 if successful, -1 if any error occurred. */ int prog_insert(STMT *stmt) { - // TO BE IMPLEMENTED - abort(); + // if no lineno, return -1 + if (!stmt->lineno) + return -1; + + // get first stmt after lineno + prog_data *ptr = prog_get_data(stmt->lineno); + + // if stmt exists + if (ptr != prog_head && ptr->stmt->lineno == stmt->lineno) + { + free_stmt(ptr->stmt); + ptr->stmt = stmt; + return 0; + } + + + // insert the new one + prog_data *new = malloc(sizeof(prog_data)); + new->next = ptr; + new->prev = ptr->prev; + new->prev->next = new; + new->next->prev = new; + new->stmt = stmt; + return 0; } /** @@ -69,8 +101,24 @@ int prog_insert(STMT *stmt) { * @param max Upper end of the range of line numbers to be deleted. */ int prog_delete(int min, int max) { - // TO BE IMPLEMENTED - abort(); + // get the stmt greater than or equal to min + prog_data *ptr = prog_get_data(min); + + // deletion + while (1) + { + // break if next stmt is head or greater than max + if (ptr == prog_head || ptr->stmt->lineno > max) + break; + // if is counter, counter move to the next stmt + if (ptr == prog_counter) + prog_counter = ptr->next; + // delete statement + ptr = ptr->next; + prog_remove_data(ptr->prev); + } + + return 0; } /** @@ -79,8 +127,7 @@ int prog_delete(int min, int max) { * before the first statement in the program. */ void prog_reset(void) { - // TO BE IMPLEMENTED - abort(); + prog_counter = prog_head->next; } /** @@ -95,8 +142,9 @@ void prog_reset(void) { * counter position, if any, otherwise NULL. */ STMT *prog_fetch(void) { - // TO BE IMPLEMENTED - abort(); + if (prog_counter != prog_head) + return prog_counter->stmt; + return NULL; } /** @@ -111,8 +159,11 @@ STMT *prog_fetch(void) { * position, if any, otherwise NULL. */ STMT *prog_next() { - // TO BE IMPLEMENTED - abort(); + // if has next + if (prog_counter != prog_head) + prog_counter = prog_counter->next; + + return prog_fetch(); } /** @@ -131,6 +182,53 @@ STMT *prog_next() { * statement exists, otherwise NULL. */ STMT *prog_goto(int lineno) { - // TO BE IMPLEMENTED - abort(); + // get first stmt with greter than or equal to lineno + prog_data *ptr = prog_get_data(lineno); + // return NULL is no such stmt exists + if (ptr == prog_head) + return NULL; + // if equal, return stmt + if (ptr->stmt->lineno == lineno) { + prog_counter = ptr; + return ptr->stmt; + } + // else return NULL + return NULL; } + +prog_data *prog_get_data(int lineno) { + // go through the double-linked list and find the fist stmt with lineno greater than or equal to lineno + prog_data *ptr = prog_head->next; + while (ptr != prog_head) + { + if (ptr->stmt->lineno >= lineno) + return ptr; + ptr = ptr->next; + } + return prog_head; +} + +void prog_remove_data(prog_data* data) { + data->prev->next = data->next; + data->next->prev = data->prev; + if (data->stmt) { + free_stmt(data->stmt); + } + free(data); +} + +void prog_init() { + prog_head = malloc(sizeof(prog_data)); + prog_head->next = prog_head; + prog_head->prev = prog_head; + prog_head->stmt = NULL; + prog_counter = prog_head; +} + +void prog_fini() { + while (prog_head->next != prog_head) + prog_remove_data(prog_head->next); + + free(prog_head); + prog_head = NULL; +} \ No newline at end of file diff --git a/hw4/src/store.c b/hw4/src/store.c index aca225e..0bbf047 100644 --- a/hw4/src/store.c +++ b/hw4/src/store.c @@ -191,14 +191,14 @@ int store_set_int(char *var, long val) { * @param f The stream to which the store contents are to be printed. */ void store_show(FILE *f) { - store_data* ptr = head->next; + store_data* ptr = store_head->next; fprintf(f, "{"); - while (ptr != head) + while (ptr != store_head) { fprintf(f, "%s=%s", ptr->name, ptr->value); ptr = ptr->next; - if ((ptr != head)) + if ((ptr != store_head)) fprintf(f, ", "); } @@ -206,17 +206,17 @@ void store_show(FILE *f) { } void store_init() { - head = malloc(sizeof(store_data)); - head->name = NULL; - head->value = NULL; - head->next = head; - head->prev = head; + store_head = malloc(sizeof(store_data)); + store_head->name = NULL; + store_head->value = NULL; + store_head->next = store_head; + store_head->prev = store_head; } store_data* store_get_data(char* var) { - store_data* ptr = head->next; + store_data* ptr = store_head->next; - while (ptr != head) + while (ptr != store_head) { if (strcmp(ptr->name, var) == 0) return ptr; @@ -238,18 +238,18 @@ void store_remove_data(store_data* data) { } void store_add_data(store_data* data) { - data->next = head->next; - data->prev = head; + data->next = store_head->next; + data->prev = store_head; data->next->prev = data; data->prev->next = data; } void store_fini() { - while (head->next != head) - store_remove_data(head->next); + while (store_head->next != store_head) + store_remove_data(store_head->next); - free(head); - head = NULL; + free(store_head); + store_head = NULL; } char* store_strcpy(char *str) {