catrm

'cat' a file, then optionally 'rm' it. I just felt like writing C.
Log | Files | Refs | Atom | README

commit 86be7e47644d3b49662200c3852d876bb50f9f09
parent d183304f9cb7af48482aa6e3c5626a5c7a0aa9de
Author: Alex Collins <alex@appsectest.com>
Date:   Thu,  3 Mar 2022 19:01:21 +0000

fixed this mess

Diffstat:
Dcat.c | 50--------------------------------------------------
Mcatrm | 0
Dcatrm.h | 18------------------
Afcat.c | 36++++++++++++++++++++++++++++++++++++
Afcat.h | 6++++++
Amain.c | 70++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Drm.c | 44--------------------------------------------
Mtest | 1+
Dtest_cat.old | 41-----------------------------------------
Dtest_rm.c | 11-----------
10 files changed, 113 insertions(+), 164 deletions(-)

diff --git a/cat.c b/cat.c @@ -1,50 +0,0 @@ -/** - * TODO -**/ - -#include "catrm.h" - -int cat(FILE *dst, FILE *src) -{ - int n = -1; - errno = 0; - - if (dst == NULL) dst = stdout; - if (src == NULL) { - errno = EBADF; - goto EXIT; - } else fseek(src, 0, SEEK_END); - - if (errno != 0) goto EXIT; - - if (ftell(src) < 1) - return EXIT_SUCCESS; - rewind(src); - - int br = -1, bw = -1; - char buf[BUFSIZ]; - do { - if (br > -1 && br != BUFSIZ) { - n = -1; - errno = EIO; - perror("invalid num. bytes read from source file"); - goto EXIT; - } - br = fread(buf, sizeof(char), BUFSIZ, src); - if (br > 0) { - bw = fwrite(buf, sizeof(char), br, dst); - if (bw != br) { - n = -1; - errno = EIO; - perror("invalid num. bytes written to destination file"); - goto EXIT; - } - n += bw; - } else { - n = 0; - } - } while (!feof(src)); - -EXIT: - return n; -} diff --git a/catrm b/catrm Binary files differ. diff --git a/catrm.h b/catrm.h @@ -1,18 +0,0 @@ -/** - * TODO -**/ - -#ifndef CATRM -#define CATRM - -#include <stdio.h> -#include <errno.h> -#include <stdlib.h> - -#define OPTS_NONE 0x00 -#define OPTS_INTERACTIVE 0x01 - -int cat(FILE *dst, FILE *src); -int rm(const char *file, const int opts); - -#endif diff --git a/fcat.c b/fcat.c @@ -0,0 +1,36 @@ +#include <stdio.h> +#include <stdlib.h> + +/* fcat copies data from file at `src` and appends it to + to the file at `dst`, in 4kb (4096) chunks. + returns EXIT_SUCCESS or EXIT_FAILURE. */ +int fcat(FILE *src, FILE *dst) +{ + int ret = EXIT_FAILURE; + size_t srcsiz; + char buf[4096]; + size_t r, w, total = 0; + + fseek(src, 0, SEEK_END); + srcsiz = ftell(src); + rewind(src); + + do { + r = fread(buf, sizeof(char), sizeof(buf), src); + if (ferror(src)) + goto ABORT; + else { + w = fwrite(buf, sizeof(char), r, dst); + if (ferror(dst)) + goto ABORT; + total += w; + } + } while (!feof(src)); + + if (total == srcsiz) + ret = EXIT_SUCCESS; + +ABORT: + return ret; +} + diff --git a/fcat.h b/fcat.h @@ -0,0 +1,6 @@ +#ifndef fcopy +#define fcopy + +int fcat(FILE *src, FILE *dst); + +#endif diff --git a/main.c b/main.c @@ -0,0 +1,70 @@ +/** + * +**/ +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include "fcat.h" + +enum OPTS { + OPTS_NONE = 0x00, + OPTS_INTERACTIVE = 0x01 +}; + + +int prompt(const char *fpath, const int opts); + + +int main(int argc, char *argv[]) +{ + int opts = OPTS_INTERACTIVE, i; + + for (i = 1; i < argc; ++i) { + if (!argv[argc] || argv[argc][0] != '-') continue; + + if (strcmp(argv[argc], "-ni") == 0) + opts |= OPTS_INTERACTIVE; + else + printf("unrecognised arg: '%s'", argv[argc]); + argv[argc] = 0; + } + + for (i = 1; i < argc; ++i) { + if (prompt(argv[i], opts) == 'y') { + if (remove(argv[argc]) != 0) + perror("remove failed"); + } + } + + return EXIT_SUCCESS; +} + +int prompt(const char *fpath, const int opts) +{ + int ret = 0; + char input; + FILE *f; + + while (ret == 0) { + printf("remove file '%s' ([y]es/[n]o/[c]at)? ", fpath); + input = fgetc(stdin); + switch (input) { + case 'y': ret = 'y'; break; + case 'n': ret = 'n'; break; + case 'c': + if ((f = fopen(fpath, "r")) == NULL) { + perror("failed to open file"); + ret = 1; + } + if (fcat(f, stdout) < 0) + perror("cat failed"); + fclose(f); + break; + default: break; + } + + while (fgetc(stdin) != '\n'); + } + + return ret; +} diff --git a/rm.c b/rm.c @@ -1,44 +0,0 @@ -/** - * -**/ - -#include "catrm.h" - -int prompt(const char *fpath); - -int rm(const char *fpath, const int opts) -{ - int n = 0; - - if (opts | OPTS_INTERACTIVE) - prompt(fpath); - - return n; -} - -int prompt(const char *fpath) -{ - int ret = 0; - char *answer = malloc(4); - FILE *f = NULL; - - while (ret == 0) { - printf("remove file '%s' ([y]es/[n]o/[c]at)? ", fpath); - fgets(answer, 4, stdin); - if (ferror(stdin)) { - perror("failed to read input"); - break; - } - switch (answer[0]) { - case 'y': ret = 'y'; break; - case 'n': ret = 'n'; break; - case 'c': - f = fopen(fpath, "r"); - if (f == NULL) - perror("failed to open file"); - if (cat(stdout, f) < 0) - perror("cat failed"); - break; - } - } -} diff --git a/test b/test @@ -0,0 +1 @@ +hello world diff --git a/test_cat.old b/test_cat.old @@ -1,41 +0,0 @@ -/** - * TODO -**/ - -#include "catrm.h" - -int main(int argc, char *argv[]) -{ - FILE *dst = fopen(argv[1], "a"); - if (dst == NULL) { - perror("failed to open dst"); - } - - while (--argc > 0) { -/* - FILE *src = fopen(argv[argc], "r"); - if (src == NULL) { - perror("failed to open src"); - return EXIT_FAILURE; - } - - if (cat(dst, src) < 0 || cat(NULL, src) < 0) { - perror("cat failed"); - return EXIT_FAILURE; - } - - if (fclose(src) == EOF) { - perror("failed to close src"); - return EXIT_FAILURE; - } -*/ - rm(argv[argc], OPTS_INTERACTIVE); - } - - if (fclose(dst) == EOF) { - perror("failed to close dst"); - return EXIT_FAILURE; - } - - return EXIT_SUCCESS; -} diff --git a/test_rm.c b/test_rm.c @@ -1,11 +0,0 @@ -/** - * TODO -**/ - -#include "catrm.h" - -int main(int argc, char *argv[]) -{ - while (--argc > 0) - rm(argv[argc], OPTS_INTERACTIVE); -}