diff options
Diffstat (limited to 'pgm3/accessed.c')
| -rw-r--r-- | pgm3/accessed.c | 122 | 
1 files changed, 122 insertions, 0 deletions
| diff --git a/pgm3/accessed.c b/pgm3/accessed.c new file mode 100644 index 0000000..b1007a9 --- /dev/null +++ b/pgm3/accessed.c @@ -0,0 +1,122 @@ +#include <errno.h> +#include <signal.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <sys/types.h> +#include <sys/stat.h> +#include <sys/sysmacros.h> +#include <time.h> +#include <unistd.h> + +#define FALSE 0 +#define FILE_BUFF 4096 +#define TRUE  1 + +struct NODE { +    char filename[FILE_BUFF]; +    int inode; +    long atime; +    struct NODE *next; +}; + +int makeList(struct NODE **head) { +    /* +     * makeList builds a linked list of nodes representing the filenames +     * given on stdin and their access time. +     */ +    char filename[FILE_BUFF]; +    int inList = FALSE; +    struct NODE *currentNode = NULL; +    struct NODE *newNode = NULL; +    struct stat statData; + +    while (scanf(" %s", filename) == 1) { + +        if (stat(filename, &statData) == 0 && S_ISREG(statData.st_mode)) { +            inList = FALSE; + +            for (currentNode = *head; currentNode != NULL; currentNode = currentNode->next) { + +                if (currentNode->inode == statData.st_ino) { +                    inList = TRUE; +                } + +            } + +            if (!inList) { +                newNode = (struct NODE *) malloc(sizeof(struct NODE)); +                newNode->inode = statData.st_ino; +                strcpy(newNode->filename, filename); +                newNode->atime = (time(NULL) - statData.st_atime) / 86400; +                newNode->next = *head; +                *head = newNode; +            } + +        } + +    } + +    return 0; +} + +int main(int argc, char *argv[]) { +    /* +     * accessed takes in filenames from stdin and one command line argument, +     * "num". It then builds a linked list of the unique, regular files and +     * prints out those files not accessed in "num" days (if num is positive) +     * or prints out those files accesssed within "num" days (if num is +     * negative). +     */ +    int accessedNum = 0; +    struct NODE *currentNode = NULL; +    struct NODE *list = NULL; + +    // Go through args +    if (argc != 2) { +        fprintf(stderr, "accessed: usage: ./accessed [num days]\n"); +        exit(1); +    } + +    accessedNum = strtol(argv[1], NULL, 10); + +    if (errno == EINVAL) { +        fprintf(stderr, "accessed: error: num must be integer type.\n"); +        exit(1); +    } +    else if (errno == ERANGE) { +        fprintf(stderr, "accessed: error: num must be of integer size.\n"); +        exit(1); +    } +    else if (accessedNum == 0) { +        fprintf(stderr, "accessed: error: num must be nonzero integer.\n"); +        exit(1); +    } + +    if (makeList(&list) != 0) { +        fprintf(stderr, "accessed: error: could not build linked list.\n"); +        exit(1); +    } + +    // print out filenames that match requested access time +    for (currentNode = list; currentNode != NULL; currentNode = currentNode->next) { + +        if (accessedNum > 0 && currentNode->atime > accessedNum) { // not within num days +            printf("%s\n", currentNode->filename); +        } + +        if (accessedNum < 0 && currentNode->atime <= (accessedNum * -1)) { // within num days +            printf("%s\n", currentNode->filename); +        } + +    } + +    // free list +    while (currentNode != NULL) { +        currentNode = list; +        list = list->next; +        free(currentNode); +    } + +    exit(0); +} |